Cataclysm BN
game Class Reference

#include <game.h>

Classes

class  Creature_range
 
class  debug_hour_timer
 
class  draw_callback_t
 
class  monster_range
 
class  non_dead_range
 
class  npc_range
 

Public Member Functions

 game ()
 
 ~game ()
 
void load_static_data ()
 Loads static data that does not depend on mods or similar. More...
 
std::string get_player_base_save_path () const
 Base path for saving player data. More...
 
std::string get_world_base_save_path () const
 Base path for saving world data. More...
 
void on_options_changed ()
 Should be invoked whenever options change. More...
 
void setup ()
 
void serialize (std::ostream &fout)
 Saving and loading functions. More...
 
void unserialize (std::istream &fin)
 
void unserialize_master (std::istream &fin)
 
bool dump_stats (const std::string &what, dump_mode mode, const std::vector< std::string > &opts)
 write statistics to stdout and More...
 
bool save ()
 Returns false if saving failed. More...
 
std::vector< std::string > list_active_saves ()
 Returns a list of currently active character saves. More...
 
void write_memorial_file (const std::string &filename, std::string sLastWords)
 Writes information about the character out to a text file timestamped with the time of the file was made. More...
 
bool cleanup_at_end ()
 
void start_calendar ()
 
bool do_turn ()
 MAIN GAME LOOP. More...
 
shared_ptr_fast< ui_adaptorcreate_or_get_main_ui_adaptor ()
 
void invalidate_main_ui_adaptor () const
 
void mark_main_ui_adaptor_resize () const
 
void draw ()
 
void draw_ter (bool draw_sounds=true)
 
void draw_ter (const tripoint &center, bool looking=false, bool draw_sounds=true)
 
void add_draw_callback (shared_ptr_fast< draw_callback_t > cb)
 
void draw_panels (bool force_draw=false)
 
std::optional< tripointget_veh_dir_indicator_location (bool next) const
 Returns the location where the indicator should go relative to the reality bubble, or nothing to indicate no indicator should be drawn. More...
 
void draw_veh_dir_indicator (bool next)
 
void vertical_move (int z, bool force, bool peeking=false)
 Moves the player vertically. More...
 
void start_hauling (const tripoint &pos)
 
std::optional< tripointfind_or_make_stairs (map &mp, int z_after, bool &rope_ladder, bool peeking)
 Returns the other end of the stairs (if any). More...
 
void vertical_shift (int z_after)
 Actual z-level movement part of vertical_move. More...
 
void vertical_notes (int z_before, int z_after)
 Add goes up/down auto_notes (if turned on) More...
 
void use_computer (const tripoint &p)
 Checks to see if a player can use a computer (not illiterate, etc.) and uses if able. More...
 
template<typename T = Creature>
T * critter_by_id (const character_id &id)
 
template<typename T = Creature>
T * critter_at (const tripoint &p, bool allow_hallucination=false)
 Returns the Creature at the given location. More...
 
template<typename T = Creature>
const T * critter_at (const tripoint &p, bool allow_hallucination=false) const
 
template<typename T = Creature>
shared_ptr_fast< T > shared_from (const T &critter)
 Returns a shared pointer to the given critter (which can be of any of the subclasses of Creature). More...
 
size_t num_creatures () const
 Returns the approximate number of creatures in the reality bubble. More...
 
bool update_zombie_pos (const monster &critter, const tripoint &pos)
 Redirects to the creature_tracker update_pos() function. More...
 
void remove_zombie (const monster &critter)
 
void clear_zombies ()
 Redirects to the creature_tracker clear() function. More...
 
bool spawn_hallucination (const tripoint &p)
 Spawns a hallucination at a determined position. More...
 
bool swap_critters (Creature &, Creature &)
 Swaps positions of two creatures. More...
 
Creature_range all_creatures ()
 Returns an anonymous range that contains all creatures. More...
 
monster_range all_monsters ()
 Same as all_creatures but iterators only over monsters. More...
 
npc_range all_npcs ()
 Same as all_creatures but iterators only over npcs. More...
 
std::vector< Creature * > get_creatures_if (const std::function< bool(const Creature &)> &pred)
 Returns all creatures matching a predicate. More...
 
std::vector< npc * > get_npcs_if (const std::function< bool(const npc &)> &pred)
 
Creatureget_creature_if (const std::function< bool(const Creature &)> &pred)
 Returns a creature matching a predicate. More...
 
bool is_empty (const tripoint &p)
 Returns true if there is no player, NPC, or monster on the tile and move_cost > 0. More...
 
bool is_in_sunlight (const tripoint &p)
 Returns true if p is outdoors and it is sunny. More...
 
bool is_sheltered (const tripoint &p)
 Returns true if p is indoors, underground, or in a car. More...
 
bool revive_corpse (const tripoint &p, item &it)
 Revives a corpse at given location. More...
 
void save_cyborg (item *cyborg, const tripoint &couch_pos, player &installer)
 Turns Broken Cyborg monster into Cyborg NPC via surgery. More...
 
bool cancel_activity_query (const std::string &text)
 Asks if the player wants to cancel their activity, and if so cancels it. More...
 
bool cancel_activity_or_ignore_query (distraction_type type, const std::string &text)
 Asks if the player wants to cancel their activity and if so cancels it. More...
 
void moving_vehicle_dismount (const tripoint &dest_loc)
 Handles players exiting from moving vehicles. More...
 
vehicleremoteveh ()
 Returns the current remotely controlled vehicle. More...
 
void setremoteveh (vehicle *veh)
 Sets the current remotely controlled vehicle. More...
 
int assign_mission_id ()
 Returns the next available mission id. More...
 
npcfind_npc (character_id id)
 Find the npc with the given ID. More...
 
void load_npcs ()
 Makes any nearby NPCs on the overmap active. More...
 
void reload_npcs ()
 Unloads, then loads the NPCs. More...
 
void add_npc_follower (const character_id &id)
 Add follower id to set of followers. More...
 
void remove_npc_follower (const character_id &id)
 Remove follower id from follower set. More...
 
std::set< character_idget_follower_list ()
 Get set of followers. More...
 
void validate_npc_followers ()
 validate list of followers to account for overmap buffers More...
 
void validate_mounted_npcs ()
 
void validate_linked_vehicles ()
 validate towed vehicles so they get linked up again after a load More...
 
void validate_camps ()
 validate camps to ensure they are on the overmap list More...
 
void autopilot_vehicles ()
 process vehicles that are following the player More...
 
void catch_a_monster (monster *fish, const tripoint &pos, player *p, const time_duration &catch_duration)
 Picks and spawns a random fish from the remaining fish list when a fish is caught. More...
 
std::unordered_set< tripointget_fishable_locations (int distance, const tripoint &fish_pos)
 Get the contiguous fishable locations starting at fish_pos, out to the specificed distance. More...
 
std::vector< monster * > get_fishable_monsters (std::unordered_set< tripoint > &fishable_locations)
 Get the fishable monsters within the provided fishable locations. More...
 
void fling_creature (Creature *c, const units::angle &dir, float flvel, bool controlled=false)
 Flings the input creature in the given direction. More...
 
float natural_light_level (int zlev) const
 
unsigned char light_level (int zlev) const
 Returns coarse number-of-squares of visibility at the current light level. More...
 
void reset_light_level ()
 
character_id assign_npc_id ()
 
Creatureis_hostile_nearby ()
 
Creatureis_hostile_very_close ()
 
point update_map (player &p)
 
point update_map (int &x, int &y)
 
void update_overmap_seen ()
 
void process_artifact (item &it, player &p)
 
void add_artifact_messages (const std::vector< art_effect_passive > &effects)
 
void add_artifact_dreams ()
 
void peek ()
 
void peek (const tripoint &p)
 
std::optional< tripointlook_debug ()
 
bool check_zone (const zone_type_id &type, const tripoint &where) const
 
bool check_near_zone (const zone_type_id &type, const tripoint &where) const
 Checks whether or not there is a zone of particular type nearby. More...
 
bool is_zones_manager_open () const
 
void zones_manager ()
 
std::optional< tripointlook_around (bool force_3d=false)
 
look_around_result look_around (bool show_window, tripoint &center, const tripoint &start_point, bool has_first_point, bool select_zone, bool peeking, bool is_moving_zone=false, const tripoint &end_point=tripoint_zero, bool force_3d=false)
 
void pre_print_all_tile_info (const tripoint &lp, const catacurses::window &w_info, int &line, int last_line, const visibility_variables &cache)
 
void print_all_tile_info (const tripoint &lp, const catacurses::window &w_look, const std::string &area_name, int column, int &line, int last_line, const visibility_variables &cache)
 
void draw_look_around_cursor (const tripoint &lp, const visibility_variables &cache)
 
void extended_description (const tripoint &p)
 Long description of (visible) things at tile. More...
 
void draw_trail_to_square (const tripoint &t, bool bDrawX)
 
item_location inv_map_splice (item_filter filter, const std::string &title, int radius=0, const std::string &none_message="")
 Custom-filtered menu for inventory and nearby items and those that within specified radius. More...
 
bool has_gametype () const
 
special_game_type gametype () const
 
void toggle_fullscreen ()
 
void toggle_pixel_minimap ()
 
void reload_tileset (std::function< void(std::string)> out)
 
void temp_exit_fullscreen ()
 
void reenter_fullscreen ()
 
void zoom_in ()
 
void zoom_out ()
 
void reset_zoom ()
 
void set_zoom (int level)
 
int get_zoom () const
 
int get_moves_since_last_save () const
 
int get_user_action_counter () const
 
bool take_screenshot (const std::string &file_path) const
 Saves a screenshot of the current viewport, as a PNG file, to the given location. More...
 
bool take_screenshot () const
 Saves a screenshot of the current viewport, as a PNG file. More...
 
int get_levx () const
 The top left corner of the reality bubble (in submaps coordinates). More...
 
int get_levy () const
 
int get_levz () const
 
void load_map (const tripoint &pos_sm, bool pump_events=false)
 Load the main map at given location, see map::load, in global, absolute submap coordinates. More...
 
void load_map (const tripoint_abs_sm &pos_sm, bool pump_events=false)
 
overmapget_cur_om () const
 The overmap which contains the center submap of the reality bubble. More...
 
std::vector< npc * > allies ()
 Get all living player allies. More...
 
void set_driving_view_offset (point p)
 
void calc_driving_offset (vehicle *veh=nullptr)
 
void toggle_gate (const tripoint &p)
 
void knockback (const tripoint &s, const tripoint &t, int force, int stun, int dam_mult, Creature *source)
 
void knockback (std::vector< tripoint > &traj, int stun, int dam_mult, Creature *source)
 
void draw_bullet (const tripoint &t, int i, const std::vector< tripoint > &trajectory, char bullet)
 
void draw_hit_mon (const tripoint &p, const monster &m, bool dead=false)
 
void draw_hit_player (const Character &p, int dam)
 
void draw_line (const tripoint &p, const tripoint &center_point, const std::vector< tripoint > &points, bool noreveal=false)
 
void draw_line (const tripoint &p, const std::vector< tripoint > &points)
 
void draw_weather (const weather_printable &wPrint)
 
void draw_sct ()
 
void draw_zones (const tripoint &start, const tripoint &end, const tripoint &offset)
 
void draw_critter (const Creature &critter, const tripoint &center)
 
void draw_critter_highlighted (const Creature &critter, const tripoint &center)
 
void draw_cursor (const tripoint &p)
 
void draw_highlight (const tripoint &p)
 
void draw_radiation_override (const tripoint &p, int rad)
 
void draw_terrain_override (const tripoint &p, const ter_id &id)
 
void draw_furniture_override (const tripoint &p, const furn_id &id)
 
void draw_graffiti_override (const tripoint &p, bool has)
 
void draw_trap_override (const tripoint &p, const trap_id &id)
 
void draw_field_override (const tripoint &p, const field_type_id &id)
 
void draw_item_override (const tripoint &p, const itype_id &id, const mtype_id &mid, bool hilite)
 
void draw_vpart_override (const tripoint &p, const vpart_id &id, int part_mod, units::angle veh_dir, bool hilite, point mount)
 
void draw_below_override (const tripoint &p, bool draw)
 
void draw_monster_override (const tripoint &p, const mtype_id &id, int count, bool more, Creature::Attitude att)
 
bool is_in_viewport (const tripoint &p, int margin=0) const
 
bool check_safe_mode_allowed (bool repeat_safe_mode_warnings=true)
 Check whether movement is allowed according to safe mode settings. More...
 
void set_safe_mode (safe_mode_type mode)
 
void exam_vehicle (vehicle &veh, point cp=point_zero)
 open vehicle interaction screen More...
 
bool forced_door_closing (const tripoint &p, const ter_id &door_type, int bash_dmg)
 
bool load (const std::string &world)
 Attempt to load first valid save (if any) in world. More...
 
bool npc_menu (npc &who)
 Returns true if the menu handled stuff and player shouldn't do anything else. More...
 
bool phasing_move (const tripoint &dest, bool via_ramp=false)
 
bool walk_move (const tripoint &dest, bool via_ramp=false)
 
void on_move_effects ()
 
point place_player (const tripoint &dest)
 
void place_player_overmap (const tripoint_abs_omt &om_dest)
 
unsigned int get_seed () const
 
void set_npcs_dirty ()
 If invoked, NPCs will be reloaded before next turn. More...
 
void set_critter_died ()
 If invoked, dead will be cleaned this turn. More...
 
void mon_info (const catacurses::window &, int hor_padding=0)
 
void mon_info_update ()
 
void cleanup_dead ()
 
bool is_dangerous_tile (const tripoint &dest_loc) const
 
std::vector< std::string > get_dangerous_tile (const tripoint &dest_loc) const
 
bool prompt_dangerous_tile (const tripoint &dest_loc) const
 
void despawn_monster (monster &critter)
 Despawn a specific monster, it's stored on the overmap. More...
 
void win ()
 Marks the game as won. More...
 
bool disable_robot (const tripoint &p)
 If there is a robot (that can be disabled), query the player and try to disable it. More...
 
void draw_pixel_minimap (const catacurses::window &w)
 
void quicksave ()
 
void disp_NPCs ()
 
void list_missions ()
 
event_busevents ()
 
stats_trackerstats ()
 
kill_trackerget_kill_tracker ()
 
memorial_loggermemorial ()
 
spell_eventsspell_events_subscriber ()
 
void display_toggle_overlay (action_id)
 
bool display_overlay_state (action_id)
 
void toggle_debug_hour_timer ()
 
tripoint mouse_edge_scrolling_terrain (input_context &ctxt)
 Used to implement mouse "edge scrolling". More...
 
tripoint mouse_edge_scrolling_overmap (input_context &ctxt)
 This variant is suitable for the overmap. More...
 
void shift_destination_preview (point delta)
 
bool slip_down ()
 Checks if player is able to successfully climb to/from some terrain and not slip down. More...
 
monsterplace_critter_at (const mtype_id &id, const tripoint &p)
 Adds critters to the reality bubble, creating them if necessary. More...
 
monsterplace_critter_at (const shared_ptr_fast< monster > &mon, const tripoint &p)
 
monsterplace_critter_around (const mtype_id &id, const tripoint &center, int radius)
 
monsterplace_critter_around (const shared_ptr_fast< monster > &mon, const tripoint &center, int radius, bool forced=false)
 
monsterplace_critter_within (const mtype_id &id, const tripoint_range< tripoint > &range)
 
monsterplace_critter_within (const shared_ptr_fast< monster > &mon, const tripoint_range< tripoint > &range)
 

Public Attributes

mapm
 
avataru
 
scent_mapscent
 
timed_event_managertimed_events
 
pimpl< Creature_trackercritter_tracker
 
pimpl< faction_managerfaction_manager_ptr
 
pimpl< drop_token_providertoken_provider_ptr
 
quit_status uquit
 Used in main.cpp to determine what type of quit is being performed. More...
 
bool new_game = false
 True if the game has just started or loaded, else false. More...
 
const scenarioscen = nullptr
 
std::vector< monstercoming_to_stairs
 
int monstairz = 0
 
tripoint ter_view_p
 
catacurses::window w_terrain
 
catacurses::window w_overmap
 
catacurses::window w_omlegend
 
catacurses::window w_minimap
 
catacurses::window w_pixel_minimap
 
point driving_view_offset
 
bool debug_pathfinding = false
 
bool debug_submap_grid_overlay = false
 
Creaturedisplaying_visibility_creature
 Creature for which to display the visibility map. More...
 
int displaying_lighting_condition = 0
 Type of lighting condition overlay to display. More...
 
bool show_panel_adm = false
 
bool right_sidebar = false
 
bool fullscreen = false
 
bool was_fullscreen = false
 
bool auto_travel_mode = false
 
bool queue_screenshot = false
 
safe_mode_type safe_mode
 
int turnssincelastmon = 0
 
int mostseen = 0
 

Private Types

enum class  vmenu_ret : int { CHANGE_TAB , QUIT , FIRE }
 

Private Member Functions

void unload_npcs ()
 Unloads all NPCs. More...
 
bool load (const save_t &name)
 
void load_master ()
 
bool start_game ()
 
bool save_factions_missions_npcs ()
 
void reset_npc_dispositions ()
 
void serialize_master (std::ostream &fout)
 
bool save_artifacts ()
 
bool save_maps ()
 
void init_autosave ()
 
void create_starting_npcs ()
 
vehicleplace_vehicle_nearby (const vproto_id &id, const point_abs_omt &origin, int min_distance, int max_distance, const std::vector< std::string > &omt_search_types={})
 
void list_items_monsters ()
 
game::vmenu_ret list_items (const std::vector< map_item_stack > &item_list)
 
std::vector< map_item_stackfind_nearby_items (int iRadius)
 
void reset_item_list_state (const catacurses::window &window, int height, bool bRadiusSort)
 
game::vmenu_ret list_monsters (const std::vector< Creature * > &monster_list)
 
bool grabbed_move (const tripoint &dp)
 Check for dangerous stuff at dest_loc, return false if the player decides not to step there. More...
 
bool grabbed_veh_move (const tripoint &dp)
 
bool grabbed_furn_move (const tripoint &dp)
 
void control_vehicle ()
 
void examine (const tripoint &p)
 
void examine ()
 
void pickup ()
 
void pickup (const tripoint &p)
 
void pickup_feet ()
 
void drop ()
 
void drop_in_direction ()
 
void butcher ()
 
void chat ()
 
void print_fields_info (const tripoint &lp, const catacurses::window &w_look, int column, int &line)
 
void print_terrain_info (const tripoint &lp, const catacurses::window &w_look, const std::string &area_name, int column, int &line)
 
void print_trap_info (const tripoint &lp, const catacurses::window &w_look, int column, int &line)
 
void print_creature_info (const Creature *creature, const catacurses::window &w_look, int column, int &line, int last_line)
 
void print_vehicle_info (const vehicle *veh, int veh_part, const catacurses::window &w_look, int column, int &line, int last_line)
 
void print_visibility_info (const catacurses::window &w_look, int column, int &line, visibility_type visibility)
 
void print_items_info (const tripoint &lp, const catacurses::window &w_look, int column, int &line, int last_line)
 
void print_graffiti_info (const tripoint &lp, const catacurses::window &w_look, int column, int &line, int last_line)
 
input_context get_player_input (std::string &action)
 
void replace_stair_monsters ()
 
void update_stair_monsters ()
 
void shift_monsters (const tripoint &shift)
 Shift all active monsters, the shift vector is the number of shifted submaps. More...
 
void perhaps_add_random_npc ()
 
void monmove ()
 
void overmap_npc_move ()
 
void process_voluntary_act_interrupt ()
 
void process_activity ()
 
void handle_key_blocking_activity ()
 
void open_consume_item_menu ()
 
bool handle_action ()
 
bool try_get_right_click_action (action_id &act, const tripoint &mouse_target)
 
bool try_get_left_click_action (action_id &act, const tripoint &mouse_target)
 
void item_action_menu ()
 
bool is_game_over ()
 
void death_screen ()
 
void win_screen ()
 
void draw_minimap ()
 
void autosave ()
 
void quickload ()
 
bool handle_mouseview (input_context &ctxt, std::string &action)
 
void display_faction_epilogues ()
 
void disp_NPC_epilogues ()
 
void display_scent ()
 
void display_temperature ()
 
void display_vehicle_ai ()
 
void display_visibility ()
 
void display_lighting ()
 
void display_radiation ()
 
void display_transparency ()
 
Creatureis_hostile_within (int distance)
 
void move_save_to_graveyard (const std::string &dirname)
 
bool save_player_data ()
 
std::pair< tripoint, tripointmouse_edge_scrolling (input_context &ctxt, int speed, const tripoint &last, bool iso)
 

Private Attributes

bool is_looking = false
 
std::vector< weak_ptr_fast< draw_callback_t > > draw_callbacks
 
std::optional< action_iddisplaying_overlays
 
class game::debug_hour_timer debug_hour_timer
 
pimpl< mapmap_ptr
 
pimpl< avataru_ptr
 
pimpl< live_viewliveview_ptr
 
live_viewliveview
 
pimpl< scent_mapscent_ptr
 
pimpl< timed_event_managertimed_event_manager_ptr
 
pimpl< event_busevent_bus_ptr
 
pimpl< stats_trackerstats_tracker_ptr
 
pimpl< kill_trackerkill_tracker_ptr
 
pimpl< achievements_trackerachievements_tracker_ptr
 
pimpl< memorial_loggermemorial_logger_ptr
 
pimpl< spell_eventsspell_events_ptr
 
pimpl< distribution_grid_trackergrid_tracker_ptr
 
pimpl< weather_managerweather_manager_ptr
 
shared_ptr_fast< playeru_shared_ptr
 
catacurses::window w_terrain_ptr
 
catacurses::window w_minimap_ptr
 
std::string sFilter
 
std::string list_item_upvote
 
std::string list_item_downvote
 
bool safe_mode_warning_logged = false
 
bool bVMonsterLookFire = false
 
character_id next_npc_id
 
std::list< shared_ptr_fast< npc > > active_npc
 
int next_mission_id = 0
 
std::set< character_idfollower_ids
 
int moves_since_last_save = 0
 
time_t last_save_timestamp
 
std::array< float, OVERMAP_LAYERSlatest_lightlevels
 
time_point remoteveh_cache_time
 
vehicleremoteveh_cache
 
bool npcs_dirty = false
 Has a NPC been spawned since last load? More...
 
bool critter_died = false
 Has anything died in this turn and needs to be cleaned up? More...
 
bool first_redraw_since_waiting_started = true
 Is this the first redraw since waiting (sleeping or activity) started. More...
 
bool zones_manager_open = false
 Is Zone manager open or not - changes graphics of some zone tiles. More...
 
std::unique_ptr< special_gamegamemode
 
int user_action_counter = 0
 
int tileset_zoom = 0
 How far the tileset should be zoomed out, 16 is default. More...
 
unsigned int seed = 0
 Seed for all the random numbers that should have consistent randomness (weather). More...
 
std::vector< tripointdestination_preview
 
std::chrono::time_point< std::chrono::steady_clock > last_mouse_edge_scroll
 
tripoint last_mouse_edge_scroll_vector_terrain
 
tripoint last_mouse_edge_scroll_vector_overmap
 
weak_ptr_fast< ui_adaptormain_ui_adaptor
 
std::unique_ptr< static_popupwait_popup
 

Friends

class editmap
 
class advanced_inventory
 
class main_menu
 
class monster_range
 
class Creature_range
 
distribution_grid_trackerget_distribution_grid_tracker ()
 Returns distribution grid tracker that is a part of the global game *g. More...
 
mapget_map ()
 
Characterget_player_character ()
 
avatarget_avatar ()
 
weather_managerget_weather ()
 

Detailed Description

Definition at line 143 of file game.h.

Member Enumeration Documentation

◆ vmenu_ret

enum class game::vmenu_ret : int
strongprivate
Enumerator
CHANGE_TAB 
QUIT 
FIRE 

Definition at line 767 of file game.h.

767 : int {
768 CHANGE_TAB,
769 QUIT,
770 FIRE, // Who knew, apparently you can do that in list_monsters
771 };

Constructor & Destructor Documentation

◆ game()

game::game ( )

Definition at line 302 of file game.cpp.

302 :
304 scent_ptr( *this ),
307 m( *map_ptr ),
308 u( *u_ptr ),
309 scent( *scent_ptr ),
311 uquit( QUIT_NO ),
312 new_game( false ),
314 mostseen( 0 ),
317 next_npc_id( 1 ),
318 next_mission_id( 1 ),
322 seed( 0 ),
323 last_mouse_edge_scroll( std::chrono::steady_clock::now() )
324{
332 world_generator = std::make_unique<worldfactory>();
333 // do nothing, everything that was in here is moved to init_data() which is called immediately after g = new game; in main.cpp
334 // The reason for this move is so that g is not uninitialized when it gets to installing the parts into vehicles.
335}
void subscribe(event_subscriber *)
Definition: event_bus.cpp:39
int mostseen
Definition: game.h:1022
pimpl< spell_events > spell_events_ptr
Definition: game.h:956
safe_mode_type safe_mode
Definition: game.h:1019
bool safe_mode_warning_logged
Definition: game.h:1033
pimpl< timed_event_manager > timed_event_manager_ptr
Definition: game.h:950
std::chrono::time_point< std::chrono::steady_clock > last_mouse_edge_scroll
Definition: game.h:1067
quit_status uquit
Used in main.cpp to determine what type of quit is being performed.
Definition: game.h:977
event_bus & events()
Definition: game.cpp:2714
pimpl< stats_tracker > stats_tracker_ptr
Definition: game.h:952
character_id next_npc_id
Definition: game.h:1035
pimpl< kill_tracker > kill_tracker_ptr
Definition: game.h:953
void reset_light_level()
Definition: game.cpp:3574
pimpl< memorial_logger > memorial_logger_ptr
Definition: game.h:955
shared_ptr_fast< player > u_shared_ptr
Definition: game.h:1024
pimpl< map > map_ptr
Definition: game.h:945
bool first_redraw_since_waiting_started
Is this the first redraw since waiting (sleeping or activity) started.
Definition: game.h:1050
pimpl< live_view > liveview_ptr
Definition: game.h:947
pimpl< achievements_tracker > achievements_tracker_ptr
Definition: game.h:954
pimpl< scent_map > scent_ptr
Definition: game.h:949
timed_event_manager & timed_events
Definition: game.h:964
unsigned int seed
Seed for all the random numbers that should have consistent randomness (weather).
Definition: game.h:1062
int next_mission_id
Definition: game.h:1037
bool new_game
True if the game has just started or loaded, else false.
Definition: game.h:979
pimpl< distribution_grid_tracker > grid_tracker_ptr
Definition: game.h:957
map & m
Definition: game.h:961
avatar & u
Definition: game.h:962
scent_map & scent
Definition: game.h:963
int user_action_counter
Definition: game.h:1056
live_view & liveview
Definition: game.h:948
int tileset_zoom
How far the tileset should be zoomed out, 16 is default.
Definition: game.h:1059
pimpl< avatar > u_ptr
Definition: game.h:946
time_point remoteveh_cache_time
Definition: game.h:1043
static void achievement_attained(const achievement *a)
Definition: game.cpp:295
static constexpr int DEFAULT_TILESET_ZOOM
Definition: game.h:41
@ SAFE_MODE_ON
Definition: game.h:78
@ QUIT_NO
Definition: game.h:68
mapbuffer MAPBUFFER
Definition: mapbuffer.cpp:40
const time_point before_time_starts
A time point that is always before the current turn, even when the game has just started.
Definition: calendar.cpp:25
For use with smart pointers when you don't actually want the deleter to do anything.
Definition: cata_utility.h:32
std::unique_ptr< worldfactory > world_generator

References achievements_tracker_ptr, events(), first_redraw_since_waiting_started, kill_tracker_ptr, memorial_logger_ptr, reset_light_level(), spell_events_ptr, stats_tracker_ptr, event_bus::subscribe(), and world_generator.

◆ ~game()

game::~game ( )
default

Member Function Documentation

◆ add_artifact_dreams()

void game::add_artifact_dreams ( )

Definition at line 11879 of file game.cpp.

11880{
11881 //If player is sleeping, get a dream from a carried artifact
11882 //Don't need to check that player is sleeping here, that's done before calling
11883 std::vector<item *> art_items = u.items_with( []( const item & it ) -> bool {
11884 return it.is_artifact();
11885 } );
11886 std::vector<item *> valid_arts;
11887 std::vector<std::vector<std::string>>
11888 valid_dreams; // Tracking separately so we only need to check its req once
11889 //Pull the list of dreams
11890 add_msg( m_debug, "Checking %s carried artifacts", art_items.size() );
11891 for( auto &it : art_items ) {
11892 //Pick only the ones with an applicable dream
11894 if( art && art->charge_req != ACR_NULL &&
11895 ( it->ammo_remaining() < it->ammo_capacity() ||
11896 it->ammo_capacity() == 0 ) ) { //or max 0 in case of wacky mod shenanigans
11897 add_msg( m_debug, "Checking artifact %s", it->tname() );
11898 if( check_art_charge_req( *it ) ) {
11899 add_msg( m_debug, " Has freq %s,%s", art->dream_freq_met, art->dream_freq_unmet );
11900 if( art->dream_freq_met > 0 && x_in_y( art->dream_freq_met, 100 ) ) {
11901 add_msg( m_debug, "Adding met dream from %s", it->tname() );
11902 valid_arts.push_back( it );
11903 valid_dreams.push_back( art->dream_msg_met );
11904 }
11905 } else {
11906 add_msg( m_debug, " Has freq %s,%s", art->dream_freq_met, art->dream_freq_unmet );
11907 if( art->dream_freq_unmet > 0 && x_in_y( art->dream_freq_unmet, 100 ) ) {
11908 add_msg( m_debug, "Adding unmet dream from %s", it->tname() );
11909 valid_arts.push_back( it );
11910 valid_dreams.push_back( art->dream_msg_unmet );
11911 }
11912 }
11913 }
11914 }
11915 if( !valid_dreams.empty() ) {
11916 add_msg( m_debug, "Found %s valid artifact dreams", valid_dreams.size() );
11917 const int selected = rng( 0, valid_arts.size() - 1 );
11918 auto it = valid_arts[selected];
11919 auto msg = random_entry( valid_dreams[selected] );
11920 const std::string &dream = string_format( _( msg ), it->tname() );
11921 add_msg( dream );
11922 } else {
11923 add_msg( m_debug, "Didn't have any dreams, sorry" );
11924 }
11925}
units::quantity< V, B > rng(const units::quantity< V, B > &min, const units::quantity< V, B > &max)
Definition: artifact.cpp:32
@ ACR_NULL
Definition: artifact.h:79
bool x_in_y(const time_duration &a, const time_duration &b)
Definition: calendar.cpp:521
This class is essentially a copyable unique pointer.
Definition: value_ptr.h:19
Definition: item.h:210
int ammo_remaining() const
Quantity of ammunition currently loaded in tool, gun or auxiliary gunmod.
Definition: item.cpp:7400
bool is_artifact() const
Definition: item.cpp:6994
int ammo_capacity() const
Maximum quantity of ammunition loadable for tool, gun or auxiliary gunmod.
Definition: item.cpp:7427
std::string tname(unsigned int quantity=1, bool with_prefix=true, unsigned int truncate=0) const
Return the (translated) item name.
Definition: item.cpp:4575
const itype * type
Definition: item.h:2170
std::vector< item * > items_with(const std::function< bool(const item &)> &filter)
Returns all items (including those within a container) matching the filter.
Definition: visitable.cpp:325
@ m_debug
Definition: enums.h:271
bool check_art_charge_req(item &it)
Definition: game.cpp:11582
void add_msg(std::string msg)
Definition: messages.cpp:910
V random_entry(const C &container, D default_value)
Returns a random entry in the container.
Definition: rng.h:88
std::string string_format(std::string_view format, Args &&...args)
Simple wrapper over string_formatter::parse.
cata::value_ptr< islot_artifact > artifact
Definition: itype.h:837
#define _(msg)
Definition: translations.h:116

References _, ACR_NULL, add_msg(), item::ammo_capacity(), item::ammo_remaining(), itype::artifact, check_art_charge_req(), item::is_artifact(), visitable< T >::items_with(), m_debug, random_entry(), rng(), string_format(), item::tname(), item::type, u, and x_in_y().

Referenced by do_turn().

◆ add_artifact_messages()

void game::add_artifact_messages ( const std::vector< art_effect_passive > &  effects)

Definition at line 11701 of file game.cpp.

11702{
11703 int net_str = 0;
11704 int net_dex = 0;
11705 int net_per = 0;
11706 int net_int = 0;
11707 int net_speed = 0;
11708
11709 for( auto &i : effects ) {
11710 switch( i ) {
11711 case AEP_STR_UP:
11712 net_str += 4;
11713 break;
11714 case AEP_DEX_UP:
11715 net_dex += 4;
11716 break;
11717 case AEP_PER_UP:
11718 net_per += 4;
11719 break;
11720 case AEP_INT_UP:
11721 net_int += 4;
11722 break;
11723 case AEP_ALL_UP:
11724 net_str += 2;
11725 net_dex += 2;
11726 net_per += 2;
11727 net_int += 2;
11728 break;
11729 case AEP_STR_DOWN:
11730 net_str -= 3;
11731 break;
11732 case AEP_DEX_DOWN:
11733 net_dex -= 3;
11734 break;
11735 case AEP_PER_DOWN:
11736 net_per -= 3;
11737 break;
11738 case AEP_INT_DOWN:
11739 net_int -= 3;
11740 break;
11741 case AEP_ALL_DOWN:
11742 net_str -= 2;
11743 net_dex -= 2;
11744 net_per -= 2;
11745 net_int -= 2;
11746 break;
11747
11748 case AEP_SPEED_UP:
11749 net_speed += 20;
11750 break;
11751 case AEP_SPEED_DOWN:
11752 net_speed -= 20;
11753 break;
11754
11755 case AEP_PBLUE:
11756 break; // No message
11757
11758 case AEP_SNAKES:
11759 add_msg( m_warning, _( "Your skin feels slithery." ) );
11760 break;
11761
11762 case AEP_INVISIBLE:
11763 add_msg( m_good, _( "You fade into invisibility!" ) );
11764 break;
11765
11766 case AEP_CLAIRVOYANCE:
11768 add_msg( m_good, _( "You can see through walls!" ) );
11769 break;
11770
11772 add_msg( m_good, _( "You can see through everything!" ) );
11773 break;
11774
11775 case AEP_STEALTH:
11776 add_msg( m_good, _( "Your steps stop making noise." ) );
11777 break;
11778
11779 case AEP_GLOW:
11780 add_msg( _( "A glow of light forms around you." ) );
11781 break;
11782
11783 case AEP_PSYSHIELD:
11784 add_msg( m_good, _( "Your mental state feels protected." ) );
11785 break;
11786
11788 add_msg( m_good, _( "You feel insulated." ) );
11789 break;
11790
11791 case AEP_CARRY_MORE:
11792 add_msg( m_good, _( "Your back feels strengthened." ) );
11793 break;
11794
11795 case AEP_FUN:
11796 add_msg( m_good, _( "You feel a pleasant tingle." ) );
11797 break;
11798
11799 case AEP_HUNGER:
11800 add_msg( m_warning, _( "You feel hungry." ) );
11801 break;
11802
11803 case AEP_THIRST:
11804 add_msg( m_warning, _( "You feel thirsty." ) );
11805 break;
11806
11807 case AEP_EVIL:
11808 add_msg( m_warning, _( "You feel an evil presence…" ) );
11809 break;
11810
11811 case AEP_SCHIZO:
11812 add_msg( m_bad, _( "You feel a tickle of insanity." ) );
11813 break;
11814
11815 case AEP_RADIOACTIVE:
11816 add_msg( m_warning, _( "Your skin prickles with radiation." ) );
11817 break;
11818
11819 case AEP_MUTAGENIC:
11820 add_msg( m_bad, _( "You feel your genetic makeup degrading." ) );
11821 break;
11822
11823 case AEP_ATTENTION:
11824 add_msg( m_warning, _( "You feel an otherworldly attention upon you…" ) );
11825 break;
11826
11827 case AEP_FORCE_TELEPORT:
11828 add_msg( m_bad, _( "You feel a force pulling you inwards." ) );
11829 break;
11830
11831 case AEP_MOVEMENT_NOISE:
11832 add_msg( m_warning, _( "You hear a rattling noise coming from inside yourself." ) );
11833 break;
11834
11835 case AEP_BAD_WEATHER:
11836 add_msg( m_warning, _( "You feel storms coming." ) );
11837 break;
11838
11839 case AEP_SICK:
11840 add_msg( m_bad, _( "You feel unwell." ) );
11841 break;
11842
11843 case AEP_SMOKE:
11844 add_msg( m_warning, _( "A cloud of smoke appears." ) );
11845 break;
11846 default:
11847 //Suppress warnings
11848 break;
11849 }
11850 }
11851
11852 std::string stat_info;
11853 if( net_str != 0 ) {
11854 stat_info += string_format( _( "Str %s%d! " ),
11855 ( net_str > 0 ? "+" : "" ), net_str );
11856 }
11857 if( net_dex != 0 ) {
11858 stat_info += string_format( _( "Dex %s%d! " ),
11859 ( net_dex > 0 ? "+" : "" ), net_dex );
11860 }
11861 if( net_int != 0 ) {
11862 stat_info += string_format( _( "Int %s%d! " ),
11863 ( net_int > 0 ? "+" : "" ), net_int );
11864 }
11865 if( net_per != 0 ) {
11866 stat_info += string_format( _( "Per %s%d! " ),
11867 ( net_per > 0 ? "+" : "" ), net_per );
11868 }
11869
11870 if( !stat_info.empty() ) {
11871 add_msg( m_neutral, stat_info );
11872 }
11873
11874 if( net_speed != 0 ) {
11875 add_msg( m_info, _( "Speed %s%d!" ), ( net_speed > 0 ? "+" : "" ), net_speed );
11876 }
11877}
@ m_good
Definition: enums.h:260
@ m_neutral
Definition: enums.h:267
@ m_info
Definition: enums.h:265
@ m_bad
Definition: enums.h:261
@ m_warning
Definition: enums.h:264
@ AEP_GLOW
Definition: enums.h:115
@ AEP_MUTAGENIC
Definition: enums.h:130
@ AEP_ALL_UP
Definition: enums.h:106
@ AEP_INT_UP
Definition: enums.h:105
@ AEP_INT_DOWN
Definition: enums.h:135
@ AEP_PER_UP
Definition: enums.h:104
@ AEP_PSYSHIELD
Definition: enums.h:116
@ AEP_CLAIRVOYANCE_PLUS
Definition: enums.h:142
@ AEP_MOVEMENT_NOISE
Definition: enums.h:139
@ AEP_STEALTH
Definition: enums.h:113
@ AEP_CARRY_MORE
Definition: enums.h:118
@ AEP_THIRST
Definition: enums.h:125
@ AEP_SPEED_UP
Definition: enums.h:107
@ AEP_EVIL
Definition: enums.h:127
@ AEP_ALL_DOWN
Definition: enums.h:136
@ AEP_DEX_UP
Definition: enums.h:103
@ AEP_SCHIZO
Definition: enums.h:128
@ AEP_DEX_DOWN
Definition: enums.h:133
@ AEP_FUN
Definition: enums.h:120
@ AEP_PER_DOWN
Definition: enums.h:134
@ AEP_FORCE_TELEPORT
Definition: enums.h:138
@ AEP_ATTENTION
Definition: enums.h:131
@ AEP_RADIOACTIVE
Definition: enums.h:129
@ AEP_SUPER_CLAIRVOYANCE
Definition: enums.h:112
@ AEP_BAD_WEATHER
Definition: enums.h:140
@ AEP_SICK
Definition: enums.h:141
@ AEP_CLAIRVOYANCE
Definition: enums.h:111
@ AEP_INVISIBLE
Definition: enums.h:110
@ AEP_STR_UP
Definition: enums.h:102
@ AEP_STR_DOWN
Definition: enums.h:132
@ AEP_HUNGER
Definition: enums.h:124
@ AEP_RESIST_ELECTRICITY
Definition: enums.h:117
@ AEP_PBLUE
Definition: enums.h:108
@ AEP_SPEED_DOWN
Definition: enums.h:137
@ AEP_SNAKES
Definition: enums.h:109
@ AEP_SMOKE
Definition: enums.h:126

References _, add_msg(), AEP_ALL_DOWN, AEP_ALL_UP, AEP_ATTENTION, AEP_BAD_WEATHER, AEP_CARRY_MORE, AEP_CLAIRVOYANCE, AEP_CLAIRVOYANCE_PLUS, AEP_DEX_DOWN, AEP_DEX_UP, AEP_EVIL, AEP_FORCE_TELEPORT, AEP_FUN, AEP_GLOW, AEP_HUNGER, AEP_INT_DOWN, AEP_INT_UP, AEP_INVISIBLE, AEP_MOVEMENT_NOISE, AEP_MUTAGENIC, AEP_PBLUE, AEP_PER_DOWN, AEP_PER_UP, AEP_PSYSHIELD, AEP_RADIOACTIVE, AEP_RESIST_ELECTRICITY, AEP_SCHIZO, AEP_SICK, AEP_SMOKE, AEP_SNAKES, AEP_SPEED_DOWN, AEP_SPEED_UP, AEP_STEALTH, AEP_STR_DOWN, AEP_STR_UP, AEP_SUPER_CLAIRVOYANCE, AEP_THIRST, m_bad, m_good, m_info, m_neutral, m_warning, and string_format().

◆ add_draw_callback()

void game::add_draw_callback ( shared_ptr_fast< draw_callback_t cb)

Definition at line 3025 of file game.cpp.

3026{
3027 draw_callbacks.erase(
3028 std::remove_if( draw_callbacks.begin(), draw_callbacks.end(),
3029 []( const weak_ptr_fast<draw_callback_t> &cbw ) {
3030 return cbw.expired();
3031 } ),
3032 draw_callbacks.end()
3033 );
3034 draw_callbacks.emplace_back( cb );
3035 cb->added = true;
3037}
void invalidate_main_ui_adaptor() const
Definition: game.cpp:2990
std::vector< weak_ptr_fast< draw_callback_t > > draw_callbacks
Definition: game.h:225
std::weak_ptr< T > weak_ptr_fast
Definition: memory_fast.h:17

References draw_callbacks, and invalidate_main_ui_adaptor().

Referenced by get_player_input(), list_items(), list_monsters(), look_around(), pickup(), and zones_manager().

◆ add_npc_follower()

void game::add_npc_follower ( const character_id id)

Add follower id to set of followers.

Definition at line 1875 of file game.cpp.

1876{
1877 follower_ids.insert( id );
1878 u.follower_ids.insert( id );
1879}
std::set< character_id > follower_ids
Definition: game.h:1038
std::set< character_id > follower_ids
Definition: player.h:261

References follower_ids, player::follower_ids, and u.

Referenced by validate_npc_followers().

◆ all_creatures()

game::Creature_range game::all_creatures ( )

Returns an anonymous range that contains all creatures.

The range allows iteration via a range-based for loop, e.g. for( Creature &critter : all_creatures() ) { ... }. One shall not store the returned range nor the iterators. One can freely remove and add creatures to the game during the iteration. Added creatures will not be iterated over.

Definition at line 12037 of file game.cpp.

12038{
12039 return Creature_range( *this );
12040}
friend class Creature_range
Definition: game.h:334

References Creature_range.

Referenced by draw_ter(), get_creature_if(), and get_creatures_if().

◆ all_monsters()

game::monster_range game::all_monsters ( )

Same as all_creatures but iterators only over monsters.

Definition at line 12042 of file game.cpp.

12043{
12044 return monster_range( *this );
12045}
friend class monster_range
Definition: game.h:333

References monster_range.

Referenced by cleanup_at_end(), disp_NPCs(), get_fishable_monsters(), monmove(), place_player_overmap(), shift_monsters(), start_game(), validate_mounted_npcs(), and vertical_move().

◆ all_npcs()

game::npc_range game::all_npcs ( )

Same as all_creatures but iterators only over npcs.

Definition at line 12047 of file game.cpp.

12048{
12049 return npc_range( *this );
12050}

Referenced by do_turn(), and get_npcs_if().

◆ allies()

std::vector< npc * > game::allies ( )

Get all living player allies.

Definition at line 11951 of file game.cpp.

11952{
11953 return get_npcs_if( [&]( const npc & guy ) {
11954 if( !guy.is_hallucination() ) {
11955 return guy.is_ally( g->u );
11956 } else {
11957 return false;
11958 }
11959 } );
11960}
std::vector< npc * > get_npcs_if(const std::function< bool(const npc &)> &pred)
Definition: game.cpp:11974
Definition: npc.h:744
bool is_hallucination() const override
Definition: npc.cpp:3285

References get_npcs_if(), and npc::is_hallucination().

◆ assign_mission_id()

int game::assign_mission_id ( )

Returns the next available mission id.

Definition at line 1863 of file game.cpp.

1864{
1865 int ret = next_mission_id;
1867 return ret;
1868}

References next_mission_id, and cata::hash64_detail::ret.

◆ assign_npc_id()

character_id game::assign_npc_id ( )

Definition at line 3582 of file game.cpp.

3583{
3585 ++next_npc_id;
3586 return ret;
3587}

References next_npc_id, and cata::hash64_detail::ret.

Referenced by load(), and start_game().

◆ autopilot_vehicles()

void game::autopilot_vehicles ( )

process vehicles that are following the player

Definition at line 1662 of file game.cpp.

1663{
1664 for( wrapped_vehicle &veh : m.get_vehicles() ) {
1665 vehicle *&v = veh.v;
1666 if( v->is_following ) {
1667 v->drive_to_local_target( m.getabs( u.pos() ), true );
1668 } else if( v->is_patrolling ) {
1669 v->autopilot_patrol();
1670 }
1671 }
1672}
const tripoint & pos() const override
Definition: character.cpp:602
tripoint getabs(const tripoint &p) const
Translates local (to this map) coordinates of a square to global absolute coordinates.
Definition: map.cpp:8407
VehicleList get_vehicles()
Definition: map.cpp:297
A vehicle as a whole with all its components.
Definition: vehicle.h:383
void autopilot_patrol()
Definition: vehicle.cpp:703
bool is_following
Definition: vehicle.h:1715
bool is_patrolling
Definition: vehicle.h:1716
void drive_to_local_target(const tripoint &target, bool follow_protocol)
Definition: vehicle.cpp:818

References vehicle::autopilot_patrol(), vehicle::drive_to_local_target(), map::get_vehicles(), map::getabs(), vehicle::is_following, vehicle::is_patrolling, m, Character::pos(), and u.

Referenced by do_turn().

◆ autosave()

void game::autosave ( )
private

Definition at line 11368 of file game.cpp.

11369{
11370 //Don't autosave if the min-autosave interval has not passed since the last autosave/quicksave.
11371 if( time( nullptr ) < last_save_timestamp + 60 * get_option<int>( "AUTOSAVE_MINUTES" ) ) {
11372 return;
11373 }
11374 quicksave(); //Driving checks are handled by quicksave()
11375}
time_t last_save_timestamp
Definition: game.h:1040
void quicksave()
Definition: game.cpp:11323
@ time
Recharges slowly with time.

References last_save_timestamp, quicksave(), and time.

Referenced by do_turn().

◆ butcher()

void game::butcher ( )
private

Definition at line 8334 of file game.cpp.

8335{
8336 static const std::string salvage_string = "salvage";
8337 if( u.controlling_vehicle ) {
8338 add_msg( m_info, _( "You can't butcher while driving!" ) );
8339 return;
8340 }
8341
8342 const int factor = u.max_quality( quality_id( "BUTCHER" ) );
8343 const int factorD = u.max_quality( quality_id( "CUT_FINE" ) );
8344 const std::string no_knife_msg = _( "You don't have a butchering tool." );
8345 const std::string no_corpse_msg = _( "There are no corpses here to butcher." );
8346
8347 //You can't butcher on sealed terrain- you have to smash/shovel/etc it open first
8348 if( m.has_flag( "SEALED", u.pos() ) ) {
8349 if( m.sees_some_items( u.pos(), u ) ) {
8350 add_msg( m_info, _( "You can't access the items here." ) );
8351 } else if( factor > INT_MIN || factorD > INT_MIN ) {
8352 add_msg( m_info, no_corpse_msg );
8353 } else {
8354 add_msg( m_info, no_knife_msg );
8355 }
8356 return;
8357 }
8358
8359 const item *first_item_without_tools = nullptr;
8360 // Indices of relevant items
8361 std::vector<map_stack::iterator> corpses;
8362 std::vector<map_stack::iterator> disassembles;
8363 std::vector<map_stack::iterator> salvageables;
8364 map_stack items = m.i_at( u.pos() );
8365 const inventory &crafting_inv = u.crafting_inventory();
8366
8367 // TODO: Properly handle different material whitelists
8368 // TODO: Improve quality of this section
8369 auto salvage_filter = []( item it ) {
8370 const auto usable = it.get_usable_item( salvage_string );
8371 return usable != nullptr;
8372 };
8373
8374 std::vector< item * > salvage_tools = u.items_with( salvage_filter );
8375 int salvage_tool_index = INT_MIN;
8376 item *salvage_tool = nullptr;
8377 const salvage_actor *salvage_iuse = nullptr;
8378 if( !salvage_tools.empty() ) {
8379 salvage_tool = salvage_tools.front();
8380 salvage_tool_index = u.get_item_position( salvage_tool );
8381 item *usable = salvage_tool->get_usable_item( salvage_string );
8382 salvage_iuse = dynamic_cast<const salvage_actor *>(
8383 usable->get_use( salvage_string )->get_actor_ptr() );
8384 }
8385
8386 // Reserve capacity for each to hold entire item set if necessary to prevent
8387 // reallocations later on
8388 corpses.reserve( items.size() );
8389 salvageables.reserve( items.size() );
8390 disassembles.reserve( items.size() );
8391
8392 // Split into corpses, disassemble-able, and salvageable items
8393 // It's not much additional work to just generate a corpse list and
8394 // clear it later, but does make the splitting process nicer.
8395 for( map_stack::iterator it = items.begin(); it != items.end(); ++it ) {
8396 if( it->is_corpse() ) {
8397 corpses.push_back( it );
8398 } else {
8399 if( ( salvage_tool_index != INT_MIN ) && salvage_iuse->valid_to_cut_up( *it ) ) {
8400 salvageables.push_back( it );
8401 }
8402 if( crafting::can_disassemble( u, *it, crafting_inv ).success() ) {
8403 disassembles.push_back( it );
8404 } else if( !first_item_without_tools ) {
8405 first_item_without_tools = &*it;
8406 }
8407 }
8408 }
8409
8410 // Clear corpses if butcher and dissect factors are INT_MIN
8411 if( factor == INT_MIN && factorD == INT_MIN ) {
8412 corpses.clear();
8413 }
8414
8415 if( corpses.empty() && disassembles.empty() && salvageables.empty() ) {
8416 if( factor > INT_MIN || factorD > INT_MIN ) {
8417 add_msg( m_info, no_corpse_msg );
8418 } else {
8419 add_msg( m_info, no_knife_msg );
8420 }
8421
8422 if( first_item_without_tools ) {
8423 add_msg( m_info, _( "You don't have the necessary tools to disassemble any items here." ) );
8424 // Just for the "You need x to disassemble y" messages
8425 const auto ret = crafting::can_disassemble( u, *first_item_without_tools, crafting_inv );
8426 if( !ret.success() ) {
8427 add_msg( m_info, "%s", ret.c_str() );
8428 }
8429 }
8430 return;
8431 }
8432
8433 Creature *hostile_critter = is_hostile_very_close();
8434 if( hostile_critter != nullptr ) {
8435 if( !query_yn( _( "You see %s nearby! Start butchering anyway?" ),
8436 hostile_critter->disp_name() ) ) {
8437 return;
8438 }
8439 }
8440
8441 // Magic indices for special butcher options
8442 enum : int {
8443 MULTISALVAGE = MAX_ITEM_IN_SQUARE + 1,
8444 MULTIBUTCHER,
8445 MULTIDISASSEMBLE_ONE,
8446 MULTIDISASSEMBLE_ALL,
8447 NUM_BUTCHER_ACTIONS
8448 };
8449 // What are we butchering (i.e.. which vector to pick indices from)
8450 enum {
8451 BUTCHER_CORPSE,
8452 BUTCHER_DISASSEMBLE,
8453 BUTCHER_SALVAGE,
8454 BUTCHER_OTHER // For multisalvage etc.
8455 } butcher_select = BUTCHER_CORPSE;
8456 // Index to std::vector of iterators...
8457 int indexer_index = 0;
8458
8459 // Generate the indexed stacks so we can display them nicely
8460 const auto disassembly_stacks = generate_butcher_stack_display( disassembles );
8461 const auto salvage_stacks = generate_butcher_stack_display( salvageables );
8462 // Always ask before cutting up/disassembly, but not before butchery
8463 size_t ret = 0;
8464 if( !corpses.empty() || !disassembles.empty() || !salvageables.empty() ) {
8465 uilist kmenu;
8466 kmenu.text = _( "Choose corpse to butcher / item to disassemble" );
8467
8468 size_t i = 0;
8469 // Add corpses, disassembleables, and salvagables to the UI
8470 add_corpses( kmenu, corpses, i );
8471 add_disassemblables( kmenu, disassembly_stacks, i );
8472 if( salvage_iuse && !salvageables.empty() ) {
8473 add_salvagables( kmenu, salvage_stacks, i, *salvage_iuse );
8474 }
8475
8476 if( corpses.size() > 1 ) {
8477 kmenu.addentry( MULTIBUTCHER, true, 'b', _( "Butcher everything" ) );
8478 }
8479 if( disassembles.size() > 1 ) {
8480 int time_to_disassemble = 0;
8481 int time_to_disassemble_all = 0;
8482 for( const auto &stack : disassembly_stacks ) {
8483 const int time = recipe_dictionary::get_uncraft( stack.first->typeId() ).time;
8484 time_to_disassemble += time;
8485 time_to_disassemble_all += time * stack.second;
8486 }
8487
8488 kmenu.addentry_col( MULTIDISASSEMBLE_ONE, true, 'D', _( "Disassemble everything once" ),
8489 to_string_clipped( time_duration::from_turns( time_to_disassemble / 100 ) ) );
8490 kmenu.addentry_col( MULTIDISASSEMBLE_ALL, true, 'd', _( "Disassemble everything recursively" ),
8491 to_string_clipped( time_duration::from_turns( time_to_disassemble_all / 100 ) ) );
8492 }
8493 if( salvage_iuse && salvageables.size() > 1 ) {
8494 int time_to_salvage = 0;
8495 for( const auto &stack : salvage_stacks ) {
8496 time_to_salvage += salvage_iuse->time_to_cut_up( *stack.first ) * stack.second;
8497 }
8498
8499 kmenu.addentry_col( MULTISALVAGE, true, 'z', _( "Cut up everything" ),
8500 to_string_clipped( time_duration::from_turns( time_to_salvage / 100 ) ) );
8501 }
8502
8503 kmenu.query();
8504
8505 if( kmenu.ret < 0 || kmenu.ret >= NUM_BUTCHER_ACTIONS ) {
8506 return;
8507 }
8508
8509 ret = static_cast<size_t>( kmenu.ret );
8510 if( ret >= MULTISALVAGE && ret < NUM_BUTCHER_ACTIONS ) {
8511 butcher_select = BUTCHER_OTHER;
8512 indexer_index = ret;
8513 } else if( ret < corpses.size() ) {
8514 butcher_select = BUTCHER_CORPSE;
8515 indexer_index = ret;
8516 } else if( ret < corpses.size() + disassembly_stacks.size() ) {
8517 butcher_select = BUTCHER_DISASSEMBLE;
8518 indexer_index = ret - corpses.size();
8519 } else if( ret < corpses.size() + disassembly_stacks.size() + salvage_stacks.size() ) {
8520 butcher_select = BUTCHER_SALVAGE;
8521 indexer_index = ret - corpses.size() - disassembly_stacks.size();
8522 } else {
8523 debugmsg( "Invalid butchery index: %d", ret );
8524 return;
8525 }
8526 }
8527
8528 if( !u.has_morale_to_craft() ) {
8529 if( butcher_select == BUTCHER_CORPSE || indexer_index == MULTIBUTCHER ) {
8530 add_msg( m_info,
8531 _( "You are not in the mood and the prospect of guts and blood on your hands convinces you to turn away." ) );
8532 } else {
8533 add_msg( m_info,
8534 _( "You are not in the mood and the prospect of work stops you before you begin." ) );
8535 }
8536 return;
8537 }
8538 const auto helpers = character_funcs::get_crafting_helpers( u );
8539 for( const npc *np : helpers ) {
8540 add_msg( m_info, _( "%s helps with this task…" ), np->name );
8541 }
8542 switch( butcher_select ) {
8543 case BUTCHER_OTHER:
8544 switch( indexer_index ) {
8545 case MULTISALVAGE:
8546 u.assign_activity( activity_id( "ACT_LONGSALVAGE" ), 0, salvage_tool_index );
8547 break;
8548 case MULTIBUTCHER:
8549 butcher_submenu( corpses );
8550 for( map_stack::iterator &it : corpses ) {
8551 u.activity.targets.emplace_back( map_cursor( u.pos() ), &*it );
8552 }
8553 break;
8554 case MULTIDISASSEMBLE_ONE:
8555 crafting::disassemble_all( u, false );
8556 break;
8557 case MULTIDISASSEMBLE_ALL:
8559 break;
8560 default:
8561 debugmsg( "Invalid butchery type: %d", indexer_index );
8562 return;
8563 }
8564 break;
8565 case BUTCHER_CORPSE: {
8566 butcher_submenu( corpses, indexer_index );
8567 u.activity.targets.emplace_back( map_cursor( u.pos() ), &*corpses[indexer_index] );
8568 }
8569 break;
8570 case BUTCHER_DISASSEMBLE: {
8571 // Pick index of first item in the disassembly stack
8572 item *const target = &*disassembly_stacks[indexer_index].first;
8574 }
8575 break;
8576 case BUTCHER_SALVAGE: {
8577 if( !salvage_iuse || !salvage_tool ) {
8578 debugmsg( "null salve_iuse or salvage_tool" );
8579 } else {
8580 // Pick index of first item in the salvage stack
8581 item *const target = &*salvage_stacks[indexer_index].first;
8582 item_location item_loc( map_cursor( u.pos() ), target );
8583 salvage_iuse->cut_up( u, *salvage_tool, item_loc );
8584 }
8585 }
8586 break;
8587 }
8588}
string_id< activity_type > activity_id
Definition: activity_type.h:15
static std::string to_string_clipped(const int num, const clipped_unit type, const clipped_align align)
Definition: calendar.cpp:228
bool controlling_vehicle
Definition: character.h:254
player_activity activity
Definition: character.h:1578
int get_item_position(const item *it) const
Returns the item position (suitable for i_at or similar) of a specific item.
Definition: character.cpp:2355
bool has_morale_to_craft() const
Definition: crafting.cpp:337
const inventory & crafting_inventory(bool clear_path)
Definition: crafting.cpp:557
void assign_activity(const activity_id &type, int moves=calendar::INDEFINITELY_LONG, int index=-1, int pos=INT_MIN, const std::string &name="")
Legacy activity assignment, does not work for any activites using the new activity_actor class and ma...
Definition: character.cpp:9192
virtual std::string disp_name(bool possessive=false, bool capitalize_first=false) const =0
Creature * is_hostile_very_close()
Definition: game.cpp:3596
A lightweight handle to an item independent of it's location Unlike a raw pointer can be (de-)seriali...
Definition: item_location.h:23
size_t size() const
Definition: item_stack.cpp:10
iterator begin()
Definition: item_stack.cpp:28
iterator end()
Definition: item_stack.cpp:33
item * get_usable_item(const std::string &use_name)
Checks this item and its contents (recursively) for types that have use_function with type use_name.
Definition: item.cpp:7991
const use_function * get_use(const std::string &use_name) const
Returns the pointer to use_function with name use_name assigned to the type of this item or any of it...
Definition: item.cpp:7965
Definition: map.h:105
bool has_flag(const std::string &flag, const tripoint &p) const
Definition: map.cpp:2375
map_stack i_at(const tripoint &p)
Definition: map.cpp:4210
bool sees_some_items(const tripoint &p, const Creature &who) const
Check if creature can see some items at p.
Definition: map.cpp:4856
std::vector< item_location > targets
static const recipe & get_uncraft(const itype_id &id)
Returns disassembly recipe (or null recipe if no match)
int time
Definition: recipe.h:61
Cuts stuff up into components.
Definition: iuse_actor.h:567
bool valid_to_cut_up(const item &it) const
int cut_up(player &p, item &it, item_location &cut) const
int time_to_cut_up(const item &it) const
static constexpr time_duration from_turns(const T t)
Named constructors to get a duration representing a multiple of the named time units.
Definition: calendar.h:204
uilist: scrolling vertical list menu
Definition: ui.h:187
int ret
Definition: ui.h:412
void addentry_col(int r, bool e, int k, const std::string &str, const std::string &column, const std::string &desc="")
Definition: ui.cpp:962
std::string text
Definition: ui.h:320
void addentry(const std::string &str)
Definition: ui.cpp:942
int max_quality(const quality_id &qual) const
Return maximum tool quality level provided by instance or INT_MIN if not found.
Definition: visitable.cpp:277
#define debugmsg(...)
Debug message of level DL::Error and class DC::DebugMsg, also includes the source file name and line,...
Definition: debug.h:75
static void butcher_submenu(const std::vector< map_stack::iterator > &corpses, int corpse=-1)
Definition: game.cpp:8184
static void add_salvagables(uilist &menu, const std::vector< std::pair< map_stack::iterator, int > > &stacks, size_t &menu_index, const salvage_actor &salvage_iuse)
Definition: game.cpp:8142
static void add_disassemblables(uilist &menu, const std::vector< std::pair< map_stack::iterator, int > > &stacks, size_t &menu_index)
Definition: game.cpp:8163
static std::vector< std::pair< map_stack::iterator, int > > generate_butcher_stack_display(const std::vector< map_stack::iterator > &its)
Definition: game.cpp:8095
static void add_corpses(uilist &menu, const std::vector< map_stack::iterator > &its, size_t &menu_index)
Definition: game.cpp:8130
static constexpr int MAX_ITEM_IN_SQUARE
void query(bool loop=true, int timeout=-1)
Handle input and update display.
Definition: ui.cpp:838
std::vector< npc * > get_crafting_helpers(const Character &who, int max)
Returns nearby NPCs ready and willing to help with crafting or some other manual task.
ret_val< bool > can_disassemble(const Character &who, const item &obj, const inventory &inv)
Check if character can disassemble an item using the given crafting inventory.
Definition: crafting.cpp:1888
bool disassemble(avatar &you)
Prompt for an item to disassemble, then start activity.
Definition: crafting.cpp:2072
bool disassemble_all(avatar &you, bool recursively)
Start an activity to disassemble all items in avatar's square.
Definition: crafting.cpp:2083
bool query_yn(const std::string &text)
Definition: output.cpp:698
iuse_actor * get_actor_ptr()
Definition: iuse.h:316
string_id< quality > quality_id
Definition: type_id.h:184

References _, Character::activity, add_corpses(), add_disassemblables(), add_msg(), add_salvagables(), uilist::addentry(), uilist::addentry_col(), Character::assign_activity(), item_stack::begin(), butcher_submenu(), crafting::can_disassemble(), Character::controlling_vehicle, Character::crafting_inventory(), salvage_actor::cut_up(), debugmsg, crafting::disassemble(), crafting::disassemble_all(), Creature::disp_name(), item_stack::end(), time_duration::from_turns(), generate_butcher_stack_display(), use_function::get_actor_ptr(), character_funcs::get_crafting_helpers(), Character::get_item_position(), recipe_dictionary::get_uncraft(), item::get_usable_item(), item::get_use(), map::has_flag(), Character::has_morale_to_craft(), map::i_at(), is_hostile_very_close(), visitable< T >::items_with(), m, m_info, MAX_ITEM_IN_SQUARE, visitable< T >::max_quality(), Character::pos(), uilist::query(), query_yn(), cata::hash64_detail::ret, uilist::ret, map::sees_some_items(), item_stack::size(), player_activity::targets, uilist::text, recipe::time, time, salvage_actor::time_to_cut_up(), to_string_clipped(), u, and salvage_actor::valid_to_cut_up().

Referenced by handle_action().

◆ calc_driving_offset()

void game::calc_driving_offset ( vehicle veh = nullptr)

Definition at line 1248 of file game.cpp.

1249{
1250 if( veh == nullptr || !get_option<bool>( "DRIVING_VIEW_OFFSET" ) ) {
1252 return;
1253 }
1254 const int g_light_level = static_cast<int>( light_level( u.posz() ) );
1255 const int light_sight_range = u.sight_range( g_light_level );
1256 int sight = std::max( veh_lumi( *veh ), light_sight_range );
1257
1258 // The maximal offset will leave at least this many tiles
1259 // between the PC and the edge of the main window.
1260 static const int border_range = 2;
1261 point max_offset( ( getmaxx( w_terrain ) + 1 ) / 2 - border_range - 1,
1262 ( getmaxy( w_terrain ) + 1 ) / 2 - border_range - 1 );
1263
1264 // velocity at or below this results in no offset at all
1265 static const float min_offset_vel = 1 * vehicles::vmiph_per_tile;
1266 // velocity at or above this results in maximal offset
1267 static const float max_offset_vel = std::min( max_offset.y, max_offset.x ) *
1269 float velocity = veh->velocity;
1270 rl_vec2d offset = veh->move_vec();
1271 if( !veh->skidding && veh->player_in_control( u ) &&
1272 std::abs( veh->cruise_velocity - veh->velocity ) < 7 * vehicles::vmiph_per_tile ) {
1273 // Use the cruise controlled velocity, but only if
1274 // it is not too different from the actual velocity.
1275 // The actual velocity changes too often (see above slowdown).
1276 // Using it makes would make the offset change far too often.
1277 offset = veh->face_vec();
1278 velocity = veh->cruise_velocity;
1279 }
1280 float rel_offset;
1281 if( std::fabs( velocity ) < min_offset_vel ) {
1282 rel_offset = 0;
1283 } else if( std::fabs( velocity ) > max_offset_vel ) {
1284 rel_offset = ( velocity > 0 ) ? 1 : -1;
1285 } else {
1286 rel_offset = ( velocity - min_offset_vel ) / ( max_offset_vel - min_offset_vel );
1287 }
1288 // Squeeze into the corners, by making the offset vector longer,
1289 // the PC is still in view as long as both offset.x and
1290 // offset.y are <= 1
1291 if( std::fabs( offset.x ) > std::fabs( offset.y ) && std::fabs( offset.x ) > 0.2 ) {
1292 offset.y /= std::fabs( offset.x );
1293 offset.x = ( offset.x > 0 ) ? +1 : -1;
1294 } else if( std::fabs( offset.y ) > 0.2 ) {
1295 offset.x /= std::fabs( offset.y );
1296 offset.y = offset.y > 0 ? +1 : -1;
1297 }
1298 offset.x *= rel_offset;
1299 offset.y *= rel_offset;
1300 offset.x *= max_offset.x;
1301 offset.y *= max_offset.y;
1302 // [ ----@---- ] sight=6
1303 // [ --@------ ] offset=2
1304 // [ -@------# ] offset=3
1305 // can see sights square in every direction, total visible area is
1306 // (2*sight+1)x(2*sight+1), but the window is only
1307 // getmaxx(w_terrain) x getmaxy(w_terrain)
1308 // The area outside of the window is maxoff (sight-getmax/2).
1309 // If that value is <= 0, the whole visible area fits the window.
1310 // don't apply the view offset at all.
1311 // If the offset is > maxoff, only apply at most maxoff, everything
1312 // above leads to invisible area in front of the car.
1313 // It will display (getmax/2+offset) squares in one direction and
1314 // (getmax/2-offset) in the opposite direction (centered on the PC).
1315 const point maxoff( ( sight * 2 + 1 - getmaxx( w_terrain ) ) / 2,
1316 ( sight * 2 + 1 - getmaxy( w_terrain ) ) / 2 );
1317 if( maxoff.x <= 0 ) {
1318 offset.x = 0;
1319 } else if( offset.x > 0 && offset.x > maxoff.x ) {
1320 offset.x = maxoff.x;
1321 } else if( offset.x < 0 && -offset.x > maxoff.x ) {
1322 offset.x = -maxoff.x;
1323 }
1324 if( maxoff.y <= 0 ) {
1325 offset.y = 0;
1326 } else if( offset.y > 0 && offset.y > maxoff.y ) {
1327 offset.y = maxoff.y;
1328 } else if( offset.y < 0 && -offset.y > maxoff.y ) {
1329 offset.y = -maxoff.y;
1330 }
1331
1332 // Turn the offset into a vector that increments the offset toward the desired position
1333 // instead of setting it there instantly, should smooth out jerkiness.
1334 const point offset_difference( -driving_view_offset + point( offset.x, offset.y ) );
1335
1336 const point offset_sign( ( offset_difference.x < 0 ) ? -1 : 1,
1337 ( offset_difference.y < 0 ) ? -1 : 1 );
1338 // Shift the current offset in the direction of the calculated offset by one tile
1339 // per draw event, but snap to calculated offset if we're close enough to avoid jitter.
1340 offset.x = ( std::abs( offset_difference.x ) > 1 ) ?
1341 ( driving_view_offset.x + offset_sign.x ) : offset.x;
1342 offset.y = ( std::abs( offset_difference.y ) > 1 ) ?
1343 ( driving_view_offset.y + offset_sign.y ) : offset.y;
1344
1345 set_driving_view_offset( point( offset.x, offset.y ) );
1346}
int posz() const override
Definition: character.h:803
int sight_range(int light_level) const override
Returns the player's sight range.
Definition: character.cpp:607
point driving_view_offset
Definition: game.h:996
catacurses::window w_terrain
Definition: game.h:986
void set_driving_view_offset(point p)
Definition: game.cpp:1599
unsigned char light_level(int zlev) const
Returns coarse number-of-squares of visibility at the current light level.
Definition: game.cpp:3568
rl_vec2d move_vec() const
rl_vec2d face_vec() const
bool skidding
Definition: vehicle.h:1731
bool player_in_control(const Character &p) const
Definition: vehicle.cpp:279
int velocity
Definition: vehicle.h:1650
int cruise_velocity
Definition: vehicle.h:1652
static int veh_lumi(vehicle &veh)
Definition: game.cpp:1230
int getmaxx(const window &win)
Definition: ncurses_def.cpp:58
int getmaxy(const window &win)
Definition: ncurses_def.cpp:63
quantity< V, U > fabs(quantity< V, U > q)
Definition: units_def.h:136
constexpr float vmiph_per_tile
Definition: vehicle.h:67
static constexpr point point_zero
Definition: point.h:260
Definition: point.h:35
int y
Definition: point.h:39
int x
Definition: point.h:38
float y
Definition: point_float.h:13
float x
Definition: point_float.h:12

References vehicle::cruise_velocity, driving_view_offset, units::fabs(), vehicle::face_vec(), catacurses::getmaxx(), catacurses::getmaxy(), light_level(), vehicle::move_vec(), vehicle::player_in_control(), point_zero, Character::posz(), set_driving_view_offset(), Character::sight_range(), vehicle::skidding, u, veh_lumi(), vehicle::velocity, vehicles::vmiph_per_tile, w_terrain, point::x, rl_vec2d::x, point::y, and rl_vec2d::y.

Referenced by do_turn().

◆ cancel_activity_or_ignore_query()

bool game::cancel_activity_or_ignore_query ( distraction_type  type,
const std::string &  text 
)

Asks if the player wants to cancel their activity and if so cancels it.

Additionally checks if the player wants to ignore further distractions.

Definition at line 1701 of file game.cpp.

1702{
1705 return false;
1706 }
1707 if( u.has_distant_destination() ) {
1708 if( cancel_auto_move( u, text ) ) {
1709 return true;
1710 } else {
1712 return false;
1713 }
1714 }
1715 const bool force_uc = get_option<bool>( "FORCE_CAPITAL_YN" );
1716 const auto &allow_key = force_uc ? input_context::disallow_lower_case
1718
1719 const auto &action = query_popup()
1720 .context( "CANCEL_ACTIVITY_OR_IGNORE_QUERY" )
1721 .message( force_uc ?
1722 pgettext( "cancel_activity_or_ignore_query",
1723 "<color_light_red>%s %s (Case Sensitive)</color>" ) :
1724 pgettext( "cancel_activity_or_ignore_query",
1725 "<color_light_red>%s %s</color>" ),
1726 text, u.activity.get_stop_phrase() )
1727 .option( "YES", allow_key )
1728 .option( "NO", allow_key )
1729 .option( "MANAGER", allow_key )
1730 .option( "IGNORE", allow_key )
1731 .query()
1732 .action;
1733
1734 if( action == "YES" ) {
1736 return true;
1737 }
1738 if( action == "IGNORE" ) {
1740 for( auto &activity : u.backlog ) {
1741 activity.ignore_distraction( type );
1742 }
1743 }
1744 if( action == "MANAGER" ) {
1747 return true;
1748 }
1749
1752
1753 return false;
1754}
void set_destination(const std::vector< tripoint > &route, const player_activity &new_destination_activity=player_activity())
void cancel_activity()
Definition: character.cpp:9235
std::vector< tripoint > & get_auto_move_route()
std::list< player_activity > backlog
Definition: character.h:1579
bool has_distant_destination() const
static const input_event_filter allow_all_keys
Definition: input.h:541
static const input_event_filter disallow_lower_case
Definition: input.h:540
bool is_distraction_ignored(distraction_type type) const
std::string get_stop_phrase() const
void ignore_distraction(distraction_type type)
UI class for displaying messages or querying player input with popups.
Definition: popup.h:39
query_popup & context(const std::string &cat)
Specify the input context.
Definition: popup.cpp:21
query_popup & option(const std::string &opt)
Specify an action as an option.
Definition: popup.cpp:28
result query()
Query until a valid action or an error happens and return the result.
Definition: popup.cpp:348
query_popup & message(const std::string &fmt, Args &&... args)
Specify the query message.
Definition: popup.h:91
@ action
Definition: dialogue.h:36
distraction_manager::distraction_manager_gui & get_distraction_manager()
static bool cancel_auto_move(player &p, const std::string &text)
Definition: game.cpp:1688
void redraw()
Invalidate the top window and redraw all invalidated windows.
Definition: ui_manager.cpp:389
void refresh_display()
Make changes made to the display visible to the user immediately.
std::string action
Definition: popup.h:68
const char * pgettext(const char *context, const char *msgid)

References action, query_popup::result::action, Character::activity, input_context::allow_all_keys, Character::backlog, Character::cancel_activity(), cancel_auto_move(), query_popup::context(), input_context::disallow_lower_case, Character::get_auto_move_route(), get_distraction_manager(), player_activity::get_stop_phrase(), Character::has_distant_destination(), player_activity::ignore_distraction(), invalidate_main_ui_adaptor(), player_activity::is_distraction_ignored(), query_popup::message(), query_popup::option(), pgettext(), query_popup::query(), ui_manager::redraw(), refresh_display(), Character::set_destination(), distraction_manager::distraction_manager_gui::show(), type, and u.

Referenced by mon_info_update(), monmove(), and process_voluntary_act_interrupt().

◆ cancel_activity_query()

bool game::cancel_activity_query ( const std::string &  text)

Asks if the player wants to cancel their activity, and if so cancels it.

Definition at line 1756 of file game.cpp.

1757{
1759 if( u.has_distant_destination() ) {
1760 if( cancel_auto_move( u, text ) ) {
1761 return true;
1762 } else {
1764 return false;
1765 }
1766 }
1767 if( !u.activity ) {
1768 return false;
1769 }
1770 if( query_yn( "%s %s", text, u.activity.get_stop_phrase() ) ) {
1774 return true;
1775 }
1776 return false;
1777}
void clear_destination()
void resume_backlog_activity()
Definition: character.cpp:9267

References Character::activity, Character::cancel_activity(), cancel_auto_move(), Character::clear_destination(), Character::get_auto_move_route(), player_activity::get_stop_phrase(), Character::has_distant_destination(), invalidate_main_ui_adaptor(), query_yn(), Character::resume_backlog_activity(), Character::set_destination(), and u.

Referenced by handle_key_blocking_activity().

◆ catch_a_monster()

void game::catch_a_monster ( monster fish,
const tripoint pos,
player p,
const time_duration catch_duration 
)

Picks and spawns a random fish from the remaining fish list when a fish is caught.

Definition at line 1674 of file game.cpp.

1676{
1677 //spawn the corpse, rotten by a part of the duration
1679 catch_duration ) ) );
1680 if( u.sees( pos ) ) {
1681 u.add_msg_if_player( m_good, _( "You caught a %s." ), fish->type->nname() );
1682 }
1683 //quietly kill the caught
1684 fish->no_corpse_quiet = true;
1685 fish->die( p );
1686}
bool sees(const tripoint &t, bool is_player=false, int range_mod=0) const override
static item make_corpse(const mtype_id &mt=string_id< mtype >::NULL_ID(), time_point turn=calendar::turn, const std::string &name="", int upgrade_time=-1)
Make a corpse of the given monster type.
Definition: item.cpp:511
item & add_item_or_charges(const tripoint &pos, item obj, bool overflow=true)
Adds an item to map tile or stacks charges.
Definition: map.cpp:4355
bool no_corpse_quiet
Definition: monster.h:482
void die(Creature *killer) override
Empty function.
Definition: monster.cpp:2298
const mtype * type
Definition: monster.h:478
void add_msg_if_player(const std::string &msg) const override
Definition: player.cpp:367
time_point turn
Definition: calendar.cpp:36
mtype_id id
Definition: mtype.h:240
std::string nname(unsigned int quantity=1) const
Definition: mtype.cpp:65

References _, map::add_item_or_charges(), player::add_msg_if_player(), monster::die(), mtype::id, m, m_good, item::make_corpse(), mtype::nname(), monster::no_corpse_quiet, rng(), Character::sees(), calendar::turn, monster::type, and u.

◆ chat()

void game::chat ( )
private

Definition at line 397 of file npctalk.cpp.

398{
399 int volume = u.get_shout_volume();
400
401 const std::vector<npc *> available = get_npcs_if( [&]( const npc & guy ) {
402 // TODO: Get rid of the z-level check when z-level vision gets "better"
403 return u.posz() == guy.posz() && u.sees( guy.pos() ) &&
404 rl_dist( u.pos(), guy.pos() ) <= SEEX * 2;
405 } );
406 const int available_count = available.size();
407 const std::vector<npc *> followers = get_npcs_if( [&]( const npc & guy ) {
408 return guy.is_player_ally() && guy.is_following() && guy.can_hear( u.pos(), volume );
409 } );
410 const int follower_count = followers.size();
411 const std::vector<npc *> guards = get_npcs_if( [&]( const npc & guy ) {
412 return guy.mission == NPC_MISSION_GUARD_ALLY &&
413 guy.companion_mission_role_id != "FACTION_CAMP" &&
414 guy.can_hear( u.pos(), volume );
415 } );
416 const int guard_count = guards.size();
417
418 if( u.has_trait( trait_PROF_FOODP ) && !( u.is_wearing( itype_id( "foodperson_mask" ) ) ||
419 u.is_wearing( itype_id( "foodperson_mask_on" ) ) ) ) {
420 u.add_msg_if_player( m_warning, _( "You can't speak without your face!" ) );
421 return;
422 }
423 std::vector<vehicle *> animal_vehicles;
424 std::vector<vehicle *> following_vehicles;
425 std::vector<vehicle *> magic_vehicles;
426 std::vector<vehicle *> magic_following_vehicles;
427 for( auto &veh : m.get_vehicles() ) {
428 auto &v = veh.v;
429 if( v->has_engine_type( fuel_type_animal, false ) && v->is_owned_by( u ) ) {
430 animal_vehicles.push_back( v );
431 if( v->is_following ) {
432 following_vehicles.push_back( v );
433 }
434 }
435 if( v->magic ) {
436 for( const vpart_reference &vp : v->get_all_parts() ) {
437 const vpart_info &vpi = vp.info();
438 if( vpi.has_flag( "MAGIC_FOLLOW" ) ) {
439 magic_vehicles.push_back( v );
440 if( v->is_following ) {
441 magic_following_vehicles.push_back( v );
442 }
443 break;
444 }
445 }
446 }
447 }
448
449 uilist nmenu;
450 nmenu.text = std::string( _( "What do you want to do?" ) );
451
452 if( !available.empty() ) {
453 nmenu.addentry( NPC_CHAT_TALK, true, 't', available_count == 1 ?
454 string_format( _( "Talk to %s" ), available.front()->name ) :
455 _( "Talk to…" )
456 );
457 }
458 nmenu.addentry( NPC_CHAT_YELL, true, 'a', _( "Yell" ) );
459 nmenu.addentry( NPC_CHAT_SENTENCE, true, 'b', _( "Yell a sentence" ) );
460 if( !animal_vehicles.empty() ) {
462 _( "Whistle at your animals pulling vehicles to follow you." ) );
463 }
464 if( !magic_vehicles.empty() ) {
466 _( "Utter a magical command that will order your magical vehicles to follow you." ) );
467 }
468 if( !magic_following_vehicles.empty() ) {
470 _( "Utter a magical command that will order your magical vehicles to stop following you." ) );
471 }
472 if( !following_vehicles.empty() ) {
474 _( "Whistle at your animals pulling vehicles to stop following you." ) );
475 }
476 if( !guards.empty() ) {
477 nmenu.addentry( NPC_CHAT_FOLLOW, true, 'f', guard_count == 1 ?
478 string_format( _( "Tell %s to follow" ), guards.front()->name ) :
479 _( "Tell someone to follow…" )
480 );
481 }
482 if( !followers.empty() ) {
483 nmenu.addentry( NPC_CHAT_GUARD, true, 'g', follower_count == 1 ?
484 string_format( _( "Tell %s to guard" ), followers.front()->name ) :
485 _( "Tell someone to guard…" )
486 );
487 nmenu.addentry( NPC_CHAT_MOVE_TO_POS, true, 'G',
488 follower_count == 1 ? string_format( _( "Tell %s to move to location" ),
489 followers.front()->get_name() ) : _( "Tell someone to move to location…" ) );
490 nmenu.addentry( NPC_CHAT_AWAKE, true, 'w', _( "Tell everyone on your team to wake up" ) );
491 nmenu.addentry( NPC_CHAT_MOUNT, true, 'M', _( "Tell everyone on your team to mount up" ) );
492 nmenu.addentry( NPC_CHAT_DISMOUNT, true, 'm', _( "Tell everyone on your team to dismount" ) );
493 nmenu.addentry( NPC_CHAT_DANGER, true, 'D',
494 _( "Tell everyone on your team to prepare for danger" ) );
495 nmenu.addentry( NPC_CHAT_CLEAR_OVERRIDES, true, 'r',
496 _( "Tell everyone on your team to relax (Clear Overrides)" ) );
497 nmenu.addentry( NPC_CHAT_ORDERS, true, 'o', _( "Tell everyone on your team to temporarily…" ) );
498 }
499 std::string message;
500 std::string yell_msg;
501 bool is_order = true;
502 nmenu.query();
503
504 if( nmenu.ret < 0 ) {
505 return;
506 }
507
508 switch( nmenu.ret ) {
509 case NPC_CHAT_TALK: {
510 const int npcselect = npc_select_menu( available, _( "Talk to whom?" ), false );
511 if( npcselect < 0 ) {
512 return;
513 }
514 available[npcselect]->talk_to_u();
515 break;
516 }
517 case NPC_CHAT_YELL:
518 is_order = false;
519 message = _( "loudly." );
520 break;
521 case NPC_CHAT_SENTENCE: {
522 std::string popupdesc = _( "Enter a sentence to yell" );
524 popup.title( _( "Yell a sentence" ) )
525 .width( 64 )
526 .description( popupdesc )
527 .identifier( "sentence" )
528 .max_length( 128 )
529 .query();
530 yell_msg = popup.text();
531 is_order = false;
532 break;
533 }
534 case NPC_CHAT_GUARD: {
535 const int npcselect = npc_select_menu( followers, _( "Who should guard here?" ) );
536 if( npcselect < 0 ) {
537 return;
538 }
539 if( npcselect == follower_count ) {
540 for( npc *them : followers ) {
542 }
543 yell_msg = _( "Everyone guard here!" );
544 } else {
545 talk_function::assign_guard( *followers[npcselect] );
546 yell_msg = string_format( _( "Guard here, %s!" ), followers[npcselect]->name );
547 }
548 break;
549 }
551 const int npcselect = npc_select_menu( followers, _( "Who should move?" ) );
552 if( npcselect < 0 ) {
553 return;
554 }
555
556 map &here = get_map();
557 std::optional<tripoint> p = look_around();
558
559 if( !p ) {
560 return;
561 }
562
563 if( here.impassable( tripoint( *p ) ) ) {
564 add_msg( m_info, _( "This destination can't be reached." ) );
565 return;
566 }
567
568 const auto &to = p.value();
569 if( npcselect == follower_count ) {
570 for( npc *them : followers ) {
571 tripoint_abs_ms( here.getabs( to ) );
572 them->goto_to_this_pos = here.getglobal( to );
573 }
574 yell_msg = _( "Everyone move there!" );
575 } else {
576 followers[npcselect]->goto_to_this_pos = here.getglobal( to );
577 yell_msg = string_format( _( "Move there, %s!" ), followers[npcselect]->get_name() );
578 }
579 break;
580 }
581 case NPC_CHAT_FOLLOW: {
582 const int npcselect = npc_select_menu( guards, _( "Who should follow you?" ) );
583 if( npcselect < 0 ) {
584 return;
585 }
586 if( npcselect == guard_count ) {
587 for( npc *them : guards ) {
589 }
590 yell_msg = _( "Everyone follow me!" );
591 } else {
592 talk_function::stop_guard( *guards[npcselect] );
593 yell_msg = string_format( _( "Follow me, %s!" ), guards[npcselect]->name );
594 }
595 break;
596 }
597 case NPC_CHAT_AWAKE:
598 for( npc *them : followers ) {
599 talk_function::wake_up( *them );
600 }
601 yell_msg = _( "Stay awake!" );
602 break;
603 case NPC_CHAT_MOUNT:
604 for( npc *them : followers ) {
605 if( them->has_effect( effect_riding ) ) {
606 continue;
607 }
609 }
610 yell_msg = _( "Mount up!" );
611 break;
613 for( npc *them : followers ) {
614 if( them->has_effect( effect_riding ) ) {
615 them->npc_dismount();
616 }
617 }
618 yell_msg = _( "Dismount!" );
619 break;
620 case NPC_CHAT_DANGER:
621 for( npc *them : followers ) {
622 them->rules.set_danger_overrides();
623 }
624 yell_msg = _( "We're in danger. Stay awake, stay close, don't go wandering off, "
625 "and don't open any doors." );
626 break;
628 for( npc *p : followers ) {
630 }
631 yell_msg = _( "As you were." );
632 break;
633 case NPC_CHAT_ORDERS:
634 npc_temp_orders_menu( followers );
635 break;
638 break;
641 break;
644 break;
647 break;
648 default:
649 return;
650 }
651
652 if( !yell_msg.empty() ) {
653 message = string_format( "\"%s\"", yell_msg );
654 }
655 if( !message.empty() ) {
656 add_msg( _( "You yell %s" ), message );
657 u.shout( string_format( _( "%s yelling %s" ), u.disp_name(), message ), is_order );
658 }
659
660 u.moves -= 100;
661}
std::string disp_name(bool possessive=false, bool capitalize_first=false) const override
Returns either "you" or the player's name.
Definition: character.cpp:581
void shout(std::string msg="", bool order=false)
Definition: character.cpp:7633
bool can_hear(const tripoint &source, int volume) const
bool is_wearing(const item &itm) const
Returns true if the player is wearing the item.
Definition: character.cpp:3235
bool has_trait(const trait_id &b) const override
Returns true if the player has the entered trait.
Definition: mutation.cpp:101
int get_shout_volume() const
Definition: character.cpp:7590
int moves
Definition: creature.h:582
std::optional< tripoint > look_around(bool force_3d=false)
Definition: game.cpp:6600
friend map & get_map()
Definition: map.cpp:148
Manage and cache data about a part of the map.
Definition: map.h:384
std::string companion_mission_role_id
Definition: npc.h:1283
npc_mission mission
Definition: npc.h:1290
bool is_player_ally() const
Definition: npc.cpp:1992
bool is_following() const
Definition: npc.cpp:2023
Shows a window querying the user for input.
bool has_flag(const std::string &flag) const
Definition: veh_type.h:336
This is a wrapper over a vehicle pointer and a reference to a part of it.
coords::coord_point< tripoint, coords::origin::abs, coords::ms > tripoint_abs_ms
Definition: coordinates.h:486
int rl_dist(const coords::coord_point< Point, Origin, Scale > &loc1, const coords::coord_point< Point, Origin, Scale > &loc2)
Definition: coordinates.h:519
static constexpr int SEEX
auto here(const Character &you) -> elevator::tiles
std::string message
Definition: mapgen.cpp:420
std::string name(type dir)
Get Human readable name of a direction.
Definition: overmap.cpp:4140
void wake_up(npc &)
void find_mount(npc &)
void clear_overrides(npc &p)
void stop_guard(npc &)
void assign_guard(npc &)
quantity< int, volume_in_milliliter_tag > volume
Definition: units_volume.h:16
@ NPC_MISSION_GUARD_ALLY
Definition: npc.h:150
static const efftype_id effect_riding("riding")
static const trait_id trait_PROF_FOODP("PROF_FOODP")
static int npc_select_menu(const std::vector< npc * > &npc_list, const std::string &prompt, const bool everyone=true)
Definition: npctalk.cpp:223
static void tell_magic_veh_stop_following()
Definition: npctalk.cpp:380
static void tell_veh_stop_following()
Definition: npctalk.cpp:343
static void assign_veh_to_follow()
Definition: npctalk.cpp:354
static void npc_temp_orders_menu(const std::vector< npc * > &npc_list)
Definition: npctalk.cpp:255
static const itype_id fuel_type_animal("animal")
@ NPC_CHAT_MOUNT
Definition: npctalk.cpp:203
@ NPC_CHAT_COMMAND_MAGIC_VEHICLE_STOP_FOLLOW
Definition: npctalk.cpp:217
@ NPC_CHAT_YELL
Definition: npctalk.cpp:197
@ NPC_CHAT_FOLLOW
Definition: npctalk.cpp:200
@ NPC_CHAT_GUARD
Definition: npctalk.cpp:199
@ NPC_CHAT_DISMOUNT
Definition: npctalk.cpp:204
@ NPC_CHAT_ANIMAL_VEHICLE_FOLLOW
Definition: npctalk.cpp:214
@ NPC_CHAT_ORDERS
Definition: npctalk.cpp:206
@ NPC_CHAT_SENTENCE
Definition: npctalk.cpp:198
@ NPC_CHAT_CLEAR_OVERRIDES
Definition: npctalk.cpp:213
@ NPC_CHAT_DANGER
Definition: npctalk.cpp:205
@ NPC_CHAT_MOVE_TO_POS
Definition: npctalk.cpp:201
@ NPC_CHAT_AWAKE
Definition: npctalk.cpp:202
@ NPC_CHAT_ANIMAL_VEHICLE_STOP_FOLLOW
Definition: npctalk.cpp:215
@ NPC_CHAT_TALK
Definition: npctalk.cpp:196
@ NPC_CHAT_COMMAND_MAGIC_VEHICLE_FOLLOW
Definition: npctalk.cpp:216
static void tell_magic_veh_to_follow()
Definition: npctalk.cpp:364
int popup(const std::string &text, PopupFlags flags)
Definition: output.cpp:764

References _, add_msg(), player::add_msg_if_player(), uilist::addentry(), talk_function::assign_guard(), assign_veh_to_follow(), available, Character::can_hear(), talk_function::clear_overrides(), npc::companion_mission_role_id, Character::disp_name(), effect_riding, talk_function::find_mount(), fuel_type_animal, get_map, get_npcs_if(), Character::get_shout_volume(), map::get_vehicles(), vpart_info::has_flag(), Character::has_trait(), anonymous_namespace{iexamine_elevator.cpp}::elevator::here(), npc::is_following(), npc::is_player_ally(), Character::is_wearing(), look_around(), m, m_info, m_warning, mapgen_defer::message, npc::mission, Creature::moves, om_direction::name(), NPC_CHAT_ANIMAL_VEHICLE_FOLLOW, NPC_CHAT_ANIMAL_VEHICLE_STOP_FOLLOW, NPC_CHAT_AWAKE, NPC_CHAT_CLEAR_OVERRIDES, NPC_CHAT_COMMAND_MAGIC_VEHICLE_FOLLOW, NPC_CHAT_COMMAND_MAGIC_VEHICLE_STOP_FOLLOW, NPC_CHAT_DANGER, NPC_CHAT_DISMOUNT, NPC_CHAT_FOLLOW, NPC_CHAT_GUARD, NPC_CHAT_MOUNT, NPC_CHAT_MOVE_TO_POS, NPC_CHAT_ORDERS, NPC_CHAT_SENTENCE, NPC_CHAT_TALK, NPC_CHAT_YELL, NPC_MISSION_GUARD_ALLY, npc_select_menu(), npc_temp_orders_menu(), popup(), Character::pos(), Character::posz(), uilist::query(), uilist::ret, rl_dist(), Character::sees(), SEEX, Character::shout(), talk_function::stop_guard(), string_format(), tell_magic_veh_stop_following(), tell_magic_veh_to_follow(), tell_veh_stop_following(), uilist::text, trait_PROF_FOODP, u, and talk_function::wake_up().

Referenced by handle_action().

◆ check_near_zone()

bool game::check_near_zone ( const zone_type_id type,
const tripoint where 
) const

Checks whether or not there is a zone of particular type nearby.

Definition at line 6050 of file game.cpp.

6051{
6052 return zone_manager::get_manager().has_near( type, m.getabs( where ) );
6053}
static zone_manager & get_manager()
Definition: clzones.cpp:127
bool has_near(const zone_type_id &type, const tripoint &where, int range=MAX_DISTANCE, const faction_id &fac=your_fac) const
Definition: clzones.cpp:703

References zone_manager::get_manager(), map::getabs(), zone_manager::has_near(), m, and type.

◆ check_safe_mode_allowed()

bool game::check_safe_mode_allowed ( bool  repeat_safe_mode_warnings = true)

Check whether movement is allowed according to safe mode settings.

Returns
true if the movement is allowed, otherwise false.

Definition at line 8590 of file game.cpp.

8591{
8592 if( !repeat_safe_mode_warnings && safe_mode_warning_logged ) {
8593 // Already warned player since safe_mode_warning_logged is set.
8594 return false;
8595 }
8596
8597 std::string msg_ignore = press_x( ACTION_IGNORE_ENEMY );
8598 if( !msg_ignore.empty() ) {
8599 std::wstring msg_ignore_wide = utf8_to_wstr( msg_ignore );
8600 // Operate on a wide-char basis to prevent corrupted multi-byte string
8601 msg_ignore_wide[0] = towlower( msg_ignore_wide[0] );
8602 msg_ignore = wstr_to_utf8( msg_ignore_wide );
8603 }
8604
8606 // Automatic and mandatory safemode. Make BLOODY sure the player notices!
8607 if( u.get_int_base() < 5 || u.has_trait( trait_id( "PROF_CHURL" ) ) ) {
8609 _( "There's an angry red dot on your body, %s to brush it off." ), msg_ignore );
8610 } else {
8612 _( "You are being laser-targeted, %s to ignore." ), msg_ignore );
8613 }
8615 return false;
8616 }
8617 if( safe_mode != SAFE_MODE_STOP ) {
8618 return true;
8619 }
8620 // Currently driving around, ignore the monster, they have no chance against a proper car anyway (-:
8621 if( u.controlling_vehicle && !get_option<bool>( "SAFEMODEVEH" ) ) {
8622 return true;
8623 }
8624 // Monsters around and we don't want to run
8625 std::string spotted_creature_name;
8626 const monster_visible_info &mon_visible = u.get_mon_visible();
8627 const auto &new_seen_mon = mon_visible.new_seen_mon;
8628
8629 if( new_seen_mon.empty() ) {
8630 // naming consistent with code in game::mon_info
8631 spotted_creature_name = _( "a survivor" );
8633 } else {
8634 spotted_creature_name = new_seen_mon.back()->name();
8635 get_safemode().lastmon_whitelist = spotted_creature_name;
8636 }
8637
8638 std::string whitelist;
8639 if( !get_safemode().empty() ) {
8640 whitelist = string_format( _( " or %s to whitelist the monster" ),
8642 }
8643
8644 const std::string msg_safe_mode = press_x( ACTION_TOGGLE_SAFEMODE );
8646 _( "Spotted %1$s--safe mode is on! (%2$s to turn it off, %3$s to ignore monster%4$s)" ),
8647 spotted_creature_name, msg_safe_mode, msg_ignore, whitelist );
8649 return false;
8650}
std::string press_x(action_id act)
Definition: action.cpp:465
@ ACTION_IGNORE_ENEMY
Ignore the enemy that triggered safemode.
Definition: action.h:217
@ ACTION_WHITELIST_ENEMY
Whitelist the enemy that triggered safemode.
Definition: action.h:219
@ ACTION_TOGGLE_SAFEMODE
Turn safemode on/off, while leaving autosafemode intact.
Definition: action.h:211
std::wstring utf8_to_wstr(const std::string &str)
std::string wstr_to_utf8(const std::wstring &wstr)
bool has_effect(const efftype_id &eff_id, body_part bp=num_bp) const
Check if creature has the matching effect.
Definition: creature.cpp:1207
int get_int_base() const override
Definition: avatar.cpp:1023
monster_visible_info & get_mon_visible()
Definition: avatar.h:226
std::string lastmon_whitelist
Definition: safemode_ui.h:87
std::string npc_type_name()
Definition: safemode_ui.cpp:44
@ gmf_bypass_cooldown
Definition: enums.h:288
static const efftype_id effect_laserlocked("laserlocked")
@ SAFE_MODE_STOP
Definition: game.h:79
safemode & get_safemode()
Definition: safemode_ui.cpp:33
Structure allowing a combination of game_message_type and game_message_flags.
Definition: enums.h:293
std::vector< shared_ptr_fast< monster > > new_seen_mon
Definition: avatar.h:41

References _, ACTION_IGNORE_ENEMY, ACTION_TOGGLE_SAFEMODE, ACTION_WHITELIST_ENEMY, add_msg(), Character::controlling_vehicle, effect_laserlocked, avatar::get_int_base(), avatar::get_mon_visible(), get_safemode(), gmf_bypass_cooldown, Creature::has_effect(), Character::has_trait(), safemode::lastmon_whitelist, m_warning, monster_visible_info::new_seen_mon, safemode::npc_type_name(), press_x(), safe_mode, SAFE_MODE_STOP, safe_mode_warning_logged, string_format(), u, utf8_to_wstr(), and wstr_to_utf8().

Referenced by handle_action().

◆ check_zone()

bool game::check_zone ( const zone_type_id type,
const tripoint where 
) const

Definition at line 6045 of file game.cpp.

6046{
6047 return zone_manager::get_manager().has( type, m.getabs( where ) );
6048}
bool has(const zone_type_id &type, const tripoint &where, const faction_id &fac=your_fac) const
Definition: clzones.cpp:695

References zone_manager::get_manager(), map::getabs(), zone_manager::has(), m, and type.

Referenced by place_player().

◆ cleanup_at_end()

bool game::cleanup_at_end ( )

Definition at line 944 of file game.cpp.

945{
946 if( uquit == QUIT_DIED || uquit == QUIT_SUICIDE ) {
947 // Put (non-hallucinations) into the overmap so they are not lost.
948 for( monster &critter : all_monsters() ) {
949 despawn_monster( critter );
950 }
951 // Reset NPC factions and disposition
953 // Save the factions', missions and set the NPC's overmap coordinates
954 // Npcs are saved in the overmap.
955 save_factions_missions_npcs(); //missions need to be saved as they are global for all saves.
956 // save artifacts.
958
959 // and the overmap, and the local map.
960 save_maps(); //Omap also contains the npcs who need to be saved.
961 }
962
963 if( uquit == QUIT_DIED || uquit == QUIT_SUICIDE ) {
964 std::vector<std::string> vRip;
965
966 int iMaxWidth = 0;
967 int iNameLine = 0;
968 int iInfoLine = 0;
969
972 if( !( u.has_trait( trait_id( "CANNIBAL" ) ) || u.has_trait( trait_id( "PSYCHOPATH" ) ) ) ) {
973 vRip.emplace_back( " _______ ___" );
974 vRip.emplace_back( " < `/ |" );
975 vRip.emplace_back( " > _ _ (" );
976 vRip.emplace_back( " | |_) | |_) |" );
977 vRip.emplace_back( " | | \\ | | |" );
978 vRip.emplace_back( " ______.__%_| |_________ __" );
979 vRip.emplace_back( " _/ \\| |" );
980 iNameLine = vRip.size();
981 vRip.emplace_back( "| <" );
982 vRip.emplace_back( "| |" );
983 iMaxWidth = utf8_width( vRip.back() );
984 vRip.emplace_back( "| |" );
985 vRip.emplace_back( "|_____.-._____ __/|_________|" );
986 vRip.emplace_back( " | |" );
987 iInfoLine = vRip.size();
988 vRip.emplace_back( " | |" );
989 vRip.emplace_back( " | <" );
990 vRip.emplace_back( " | |" );
991 vRip.emplace_back( " | _ |" );
992 vRip.emplace_back( " |__/ |" );
993 vRip.emplace_back( " % / `--. |%" );
994 vRip.emplace_back( " * .%%| -< @%%%" ); // NOLINT(cata-text-style)
995 vRip.emplace_back( " `\\%`@| |@@%@%%" );
996 vRip.emplace_back( " .%%%@@@|% ` % @@@%%@%%%%" );
997 vRip.emplace_back( " _.%%%%%%@@@@@@%%%__/\\%@@%%@@@@@@@%%%%%%" );
998
999 } else {
1000 vRip.emplace_back( " _______ ___" );
1001 vRip.emplace_back( " | \\/ |" );
1002 vRip.emplace_back( " | |" );
1003 vRip.emplace_back( " | |" );
1004 iInfoLine = vRip.size();
1005 vRip.emplace_back( " | |" );
1006 vRip.emplace_back( " | |" );
1007 vRip.emplace_back( " | |" );
1008 vRip.emplace_back( " | |" );
1009 vRip.emplace_back( " | <" );
1010 vRip.emplace_back( " | _ |" );
1011 vRip.emplace_back( " |__/ |" );
1012 vRip.emplace_back( " ______.__%_| |__________ _" );
1013 vRip.emplace_back( " _/ \\| \\" );
1014 iNameLine = vRip.size();
1015 vRip.emplace_back( "| <" );
1016 vRip.emplace_back( "| |" );
1017 iMaxWidth = utf8_width( vRip.back() );
1018 vRip.emplace_back( "| |" );
1019 vRip.emplace_back( "|_____.-._______ __/|__________|" );
1020 vRip.emplace_back( " % / `_-. _ |%" );
1021 vRip.emplace_back( " * .%%| |_) | |_)< @%%%" ); // NOLINT(cata-text-style)
1022 vRip.emplace_back( " `\\%`@| | \\ | | |@@%@%%" );
1023 vRip.emplace_back( " .%%%@@@|% ` % @@@%%@%%%%" );
1024 vRip.emplace_back( " _.%%%%%%@@@@@@%%%__/\\%@@%%@@@@@@@%%%%%%" );
1025 }
1026 } else {
1027 vRip.emplace_back( R"( _________ ____ )" );
1028 vRip.emplace_back( R"( _/ `/ \_ )" );
1029 vRip.emplace_back( R"( _/ _ _ \_. )" );
1030 vRip.emplace_back( R"( _%\ |_) | |_) \_ )" );
1031 vRip.emplace_back( R"( _/ \/ | \ | | \_ )" );
1032 vRip.emplace_back( R"( _/ \_ )" );
1033 vRip.emplace_back( R"(| |)" );
1034 iNameLine = vRip.size();
1035 vRip.emplace_back( R"( ) < )" );
1036 vRip.emplace_back( R"(| |)" );
1037 vRip.emplace_back( R"(| |)" );
1038 vRip.emplace_back( R"(| _ |)" );
1039 vRip.emplace_back( R"(|__/ |)" );
1040 iMaxWidth = utf8_width( vRip.back() );
1041 vRip.emplace_back( R"( / `--. |)" );
1042 vRip.emplace_back( R"(| ( )" );
1043 iInfoLine = vRip.size();
1044 vRip.emplace_back( R"(| |)" );
1045 vRip.emplace_back( R"(| |)" );
1046 vRip.emplace_back( R"(| % . |)" );
1047 vRip.emplace_back( R"(| @` %% |)" );
1048 vRip.emplace_back( R"(| %@%@%\ * %`%@%|)" );
1049 vRip.emplace_back( R"(%%@@@.%@%\%% `\ %%.%%@@%@)" );
1050 vRip.emplace_back( R"(@%@@%%%%%@@@@@@%%%%%%%%@@%%@@@%%%@%%@)" );
1051 }
1052
1053 const int iOffsetX = TERMX > FULL_SCREEN_WIDTH ? ( TERMX - FULL_SCREEN_WIDTH ) / 2 : 0;
1054 const int iOffsetY = TERMY > FULL_SCREEN_HEIGHT ? ( TERMY - FULL_SCREEN_HEIGHT ) / 2 : 0;
1055
1057 point( iOffsetX, iOffsetY ) );
1058 draw_border( w_rip );
1059
1060 sfx::do_player_death_hurt( g->u, true );
1065
1066 for( size_t iY = 0; iY < vRip.size(); ++iY ) {
1067 size_t iX = 0;
1068 const char *str = vRip[iY].data();
1069 for( int slen = vRip[iY].size(); slen > 0; ) {
1070 const uint32_t cTemp = UTF8_getch( &str, &slen );
1071 if( cTemp != U' ' ) {
1072 nc_color ncColor = c_light_gray;
1073
1074 if( cTemp == U'%' ) {
1075 ncColor = c_green;
1076
1077 } else if( cTemp == U'_' || cTemp == U'|' ) {
1078 ncColor = c_white;
1079
1080 } else if( cTemp == U'@' ) {
1081 ncColor = c_brown;
1082
1083 } else if( cTemp == U'*' ) {
1084 ncColor = c_red;
1085 }
1086
1087 mvwputch( w_rip, point( iX + FULL_SCREEN_WIDTH / 2 - ( iMaxWidth / 2 ), iY + 1 ), ncColor,
1088 cTemp );
1089 }
1090 iX += mk_wcwidth( cTemp );
1091 }
1092 }
1093
1094 std::string sTemp;
1095
1096 center_print( w_rip, iInfoLine++, c_white, _( "Survived:" ) );
1097
1099 const int minutes = to_minutes<int>( survived ) % 60;
1100 const int hours = to_hours<int>( survived ) % 24;
1101 const int days = to_days<int>( survived );
1102
1103 if( days > 0 ) {
1104 sTemp = string_format( "%dd %dh %dm", days, hours, minutes );
1105 } else if( hours > 0 ) {
1106 sTemp = string_format( "%dh %dm", hours, minutes );
1107 } else {
1108 sTemp = string_format( "%dm", minutes );
1109 }
1110
1111 center_print( w_rip, iInfoLine++, c_white, sTemp );
1112
1113 const int iTotalKills = get_kill_tracker().monster_kill_count();
1114
1115 sTemp = _( "Kills:" );
1116 mvwprintz( w_rip, point( FULL_SCREEN_WIDTH / 2 - 5, 1 + iInfoLine++ ), c_light_gray,
1117 ( sTemp + " " ) );
1118 wprintz( w_rip, c_magenta, "%d", iTotalKills );
1119
1120 sTemp = _( "In memory of:" );
1121 mvwprintz( w_rip, point( FULL_SCREEN_WIDTH / 2 - utf8_width( sTemp ) / 2, iNameLine++ ),
1123 sTemp );
1124
1125 sTemp = u.name;
1126 mvwprintz( w_rip, point( FULL_SCREEN_WIDTH / 2 - utf8_width( sTemp ) / 2, iNameLine++ ), c_white,
1127 sTemp );
1128
1129 sTemp = _( "Last Words:" );
1130 mvwprintz( w_rip, point( FULL_SCREEN_WIDTH / 2 - utf8_width( sTemp ) / 2, iNameLine++ ),
1132 sTemp );
1133
1134 int iStartX = FULL_SCREEN_WIDTH / 2 - ( ( iMaxWidth - 4 ) / 2 );
1135 std::string sLastWords = string_input_popup()
1136 .window( w_rip, point( iStartX, iNameLine ), iStartX + iMaxWidth - 4 - 1 )
1137 .max_length( iMaxWidth - 4 - 1 )
1138 .query_string();
1139 death_screen();
1140 const bool is_suicide = uquit == QUIT_SUICIDE;
1141 events().send<event_type::game_over>( is_suicide, sLastWords );
1142 // Struck the save_player_data here to forestall Weirdness
1143 std::string char_filename = generate_memorial_filename( u.name );
1144 move_save_to_graveyard( char_filename );
1145 write_memorial_file( char_filename, sLastWords );
1146 memorial().clear();
1147 std::vector<std::string> characters = list_active_saves();
1148 // remove current player from the active characters list, as they are dead
1149 std::vector<std::string>::iterator curchar = std::find( characters.begin(),
1150 characters.end(), u.get_save_id() );
1151 if( curchar != characters.end() ) {
1152 characters.erase( curchar );
1153 }
1154
1155 if( characters.empty() ) {
1156 bool queryDelete = false;
1157 bool queryReset = false;
1158
1159 if( get_option<std::string>( "WORLD_END" ) == "query" ) {
1160 bool decided = false;
1161 std::string buffer = _( "Warning: NPC interactions and some other global flags "
1162 "will not all reset when starting a new character in an "
1163 "already-played world. This can lead to some strange "
1164 "behavior.\n\n"
1165 "Are you sure you wish to keep this world?"
1166 );
1167
1168 while( !decided ) {
1169 uilist smenu;
1170 smenu.allow_cancel = false;
1171 smenu.addentry( 0, true, 'r', "%s", _( "Reset world" ) );
1172 smenu.addentry( 1, true, 'd', "%s", _( "Delete world" ) );
1173 smenu.addentry( 2, true, 'k', "%s", _( "Keep world" ) );
1174 smenu.query();
1175
1176 switch( smenu.ret ) {
1177 case 0:
1178 queryReset = true;
1179 decided = true;
1180 break;
1181 case 1:
1182 queryDelete = true;
1183 decided = true;
1184 break;
1185 case 2:
1186 decided = query_yn( buffer );
1187 break;
1188 }
1189 }
1190 }
1191
1192 if( queryDelete || get_option<std::string>( "WORLD_END" ) == "delete" ) {
1193 world_generator->delete_world( world_generator->active_world->world_name, true );
1194
1195 } else if( queryReset || get_option<std::string>( "WORLD_END" ) == "reset" ) {
1196 world_generator->delete_world( world_generator->active_world->world_name, false );
1197 }
1198 } else if( get_option<std::string>( "WORLD_END" ) != "keep" ) {
1199 std::string tmpmessage;
1200 for( auto &character : characters ) {
1201 tmpmessage += "\n ";
1202 tmpmessage += character;
1203 }
1204 popup( _( "World retained. Characters remaining:%s" ), tmpmessage );
1205 }
1206 if( gamemode ) {
1207 gamemode = std::make_unique<special_game>(); // null gamemode or something..
1208 }
1209 }
1210
1211 //Reset any offset due to driving
1213
1214 //clear all sound channels
1220
1221 MAPBUFFER.clear();
1223
1224#if defined(__ANDROID__)
1225 quick_shortcuts_map.clear();
1226#endif
1227 return true;
1228}
uint32_t UTF8_getch(const char **src, int *srclen)
Definition: catacharset.cpp:18
int utf8_width(const char *s, const bool ignore_tags)
std::string name
Definition: character.h:1566
std::string get_save_id() const
Definition: avatar.h:88
A wrapper over a pointer to a curses window.
Definition: cursesdef.h:55
void send(const cata::event &) const
Definition: event_bus.cpp:58
void move_save_to_graveyard(const std::string &dirname)
Definition: game.cpp:2472
bool save_maps()
Definition: game.cpp:2675
std::unique_ptr< special_game > gamemode
Definition: game.h:1054
void death_screen()
Definition: game.cpp:2421
monster_range all_monsters()
Same as all_creatures but iterators only over monsters.
Definition: game.cpp:12042
bool save_factions_missions_npcs()
Definition: game.cpp:2661
void despawn_monster(monster &critter)
Despawn a specific monster, it's stored on the overmap.
Definition: game.cpp:11051
void write_memorial_file(const std::string &filename, std::string sLastWords)
Writes information about the character out to a text file timestamped with the time of the file was m...
Definition: game.cpp:2790
std::vector< std::string > list_active_saves()
Returns a list of currently active character saves.
Definition: game.cpp:2775
bool save_artifacts()
Definition: game.cpp:2669
kill_tracker & get_kill_tracker()
Definition: game.cpp:2724
memorial_logger & memorial()
Definition: game.cpp:2729
void reset_npc_dispositions()
Definition: game.cpp:2633
int monster_kill_count() const
void clear()
Delete all buffered submaps.
Definition: mapbuffer.cpp:45
string_input_popup & window(const catacurses::window &w, point start, int endx)
Set the window area where to display the input text.
string_input_popup & max_length(int value)
Maximal amount of Unicode characters that can be given by the user.
const std::string & query_string(bool loop=true, bool draw_only=false)
A duration defined as a number of specific time units.
Definition: calendar.h:180
bool allow_cancel
Definition: ui.h:362
bool has_amount(const itype_id &what, int qty, bool pseudo=true, const std::function< bool(const item &)> &filter=return_true< item >) const
Check instance provides at least qty of an item (.
Definition: visitable.cpp:1112
#define c_white
Definition: color.h:18
#define c_light_gray
Definition: color.h:19
#define c_green
Definition: color.h:22
#define c_magenta
Definition: color.h:25
#define c_brown
Definition: color.h:26
#define c_red
Definition: color.h:21
static const itype_id itype_holybook_bible1("holybook_bible1")
static std::string generate_memorial_filename(const std::string &char_name)
Definition: game.cpp:917
static const itype_id itype_holybook_bible2("holybook_bible2")
static const itype_id itype_holybook_bible3("holybook_bible3")
std::unique_ptr< game > g
Definition: game.cpp:285
@ QUIT_DIED
Definition: game.h:72
@ QUIT_SUICIDE
Definition: game.h:69
const time_point & start_of_cataclysm
Definition: calendar.cpp:33
window newwin(int nlines, int ncols, point begin)
Definition: ncurses_def.cpp:34
FMT_CONSTEXPR bool find(Ptr first, Ptr last, T value, Ptr &out)
const size_t size
Definition: om_direction.h:28
void do_player_death_hurt(const player &target, bool death)
Definition: sounds.cpp:1632
void fade_audio_channel(channel channel, int duration)
Definition: sounds.cpp:1617
void fade_audio_group(group group, int duration)
Definition: sounds.cpp:1616
int TERMX
Definition: output.cpp:47
void mvwprintz(const catacurses::window &w, point p, const nc_color &FG, const std::string &text)
Definition: output.cpp:2081
int FULL_SCREEN_HEIGHT
Definition: output.cpp:56
int TERMY
Definition: output.cpp:48
void center_print(const catacurses::window &w, const int y, const nc_color &FG, const std::string &text)
Definition: output.cpp:446
void mvwputch(const catacurses::window &w, point p, nc_color FG, int ch)
Definition: output.cpp:477
void wprintz(const catacurses::window &w, const nc_color &FG, const std::string &text)
Definition: output.cpp:2089
int FULL_SCREEN_WIDTH
Definition: output.cpp:55
void draw_border(const catacurses::window &w, nc_color border_color, const std::string &title, nc_color title_color)
Definition: output.cpp:575
overmapbuffer overmap_buffer
int mk_wcwidth(uint32_t ucs)
Definition: wcwidth.cpp:94

References _, uilist::addentry(), all_monsters(), uilist::allow_cancel, sfx::any, c_brown, c_green, c_light_gray, c_magenta, c_red, c_white, center_print(), mapbuffer::clear(), memorial_logger::clear(), overmapbuffer::clear(), sfx::context_themes, death_screen(), despawn_monster(), sfx::do_player_death_hurt(), draw_border(), events(), sfx::fade_audio_channel(), sfx::fade_audio_group(), sfx::fatigue, detail::find(), FULL_SCREEN_HEIGHT, FULL_SCREEN_WIDTH, g, game_over, gamemode, generate_memorial_filename(), get_kill_tracker(), avatar::get_save_id(), visitable< T >::has_amount(), Character::has_trait(), itype_holybook_bible1, itype_holybook_bible2, itype_holybook_bible3, list_active_saves(), MAPBUFFER, string_input_popup::max_length(), memorial(), mk_wcwidth(), kill_tracker::monster_kill_count(), move_save_to_graveyard(), mvwprintz(), mvwputch(), Character::name, catacurses::newwin(), overmap_buffer, point_zero, popup(), uilist::query(), string_input_popup::query_string(), query_yn(), QUIT_DIED, QUIT_SUICIDE, reset_npc_dispositions(), uilist::ret, save_artifacts(), save_factions_missions_npcs(), save_maps(), event_bus::send(), set_driving_view_offset(), om_direction::size, calendar::start_of_cataclysm, string_format(), TERMX, TERMY, sfx::time_of_day, calendar::turn, u, uquit, UTF8_getch(), utf8_width(), sfx::weather, string_input_popup::window(), world_generator, wprintz(), and write_memorial_file().

Referenced by do_turn().

◆ cleanup_dead()

void game::cleanup_dead ( )

Definition at line 4044 of file game.cpp.

4045{
4046 // Dead monsters need to stay in the tracker until everything else that needs to die does so
4047 // This is because dying monsters can still interact with other dying monsters (@ref Creature::killer)
4048 bool monster_is_dead = critter_tracker->kill_marked_for_death();
4049
4050 bool npc_is_dead = false;
4051 // can't use all_npcs as that does not include dead ones
4052 for( const auto &n : active_npc ) {
4053 if( n->is_dead() ) {
4054 n->die( nullptr ); // make sure this has been called to create corpses etc.
4055 npc_is_dead = true;
4056 }
4057 }
4058
4059 if( monster_is_dead ) {
4060 // From here on, pointers to creatures get invalidated as dead creatures get removed.
4061 critter_tracker->remove_dead();
4062 }
4063
4064 if( npc_is_dead ) {
4065 for( auto it = active_npc.begin(); it != active_npc.end(); ) {
4066 if( ( *it )->is_dead() ) {
4067 remove_npc_follower( ( *it )->getID() );
4068 overmap_buffer.remove_npc( ( *it )->getID() );
4069 it = active_npc.erase( it );
4070 } else {
4071 it++;
4072 }
4073 }
4074 }
4075
4076 critter_died = false;
4077}
void remove_npc_follower(const character_id &id)
Remove follower id from follower set.
Definition: game.cpp:1881
pimpl< Creature_tracker > critter_tracker
Definition: game.h:972
std::list< shared_ptr_fast< npc > > active_npc
Definition: game.h:1036
bool critter_died
Has anything died in this turn and needs to be cleaned up?
Definition: game.h:1048
shared_ptr_fast< npc > remove_npc(const character_id &id)
Find npc by id and if found, erase it from the npc list and return it ( or return nullptr if not foun...

References active_npc, critter_died, critter_tracker, overmap_buffer, overmapbuffer::remove_npc(), and remove_npc_follower().

Referenced by do_turn(), and monmove().

◆ clear_zombies()

void game::clear_zombies ( )

Redirects to the creature_tracker clear() function.

Definition at line 4740 of file game.cpp.

4741{
4742 critter_tracker->clear();
4743}

References critter_tracker.

Referenced by setup().

◆ control_vehicle()

void game::control_vehicle ( )
private

Definition at line 5184 of file game.cpp.

5185{
5186 static const itype_id fuel_type_animal( "animal" );
5187 int veh_part = -1;
5188 vehicle *veh = remoteveh();
5189 if( veh == nullptr ) {
5190 if( const optional_vpart_position vp = m.veh_at( u.pos() ) ) {
5191 veh = &vp->vehicle();
5192 veh_part = vp->part_index();
5193 }
5194 }
5195 if( veh != nullptr && veh->player_in_control( u ) &&
5196 veh->avail_part_with_feature( veh_part, "CONTROLS", true ) >= 0 ) {
5197 veh->use_controls( u.pos() );
5198 } else if( veh && veh->player_in_control( u ) &&
5199 veh->avail_part_with_feature( veh_part, "CONTROL_ANIMAL", true ) >= 0 ) {
5200 u.controlling_vehicle = false;
5201 add_msg( m_info, _( "You let go of the reins." ) );
5202 } else if( veh && ( veh->avail_part_with_feature( veh_part, "CONTROLS", true ) >= 0 ||
5203 ( veh->avail_part_with_feature( veh_part, "CONTROL_ANIMAL", true ) >= 0 &&
5204 veh->has_engine_type( fuel_type_animal, false ) && veh->has_harnessed_animal() ) ) &&
5205 u.in_vehicle ) {
5206 if( u.has_trait( trait_WAYFARER ) ) {
5207 add_msg( m_info, _( "You refuse to take control of this vehicle." ) );
5208 return;
5209 }
5210 if( !veh->interact_vehicle_locked() ) {
5211 veh->handle_potential_theft( u );
5212 return;
5213 }
5214 if( veh->engine_on ) {
5215 if( !veh->handle_potential_theft( u ) ) {
5216 return;
5217 }
5218 u.controlling_vehicle = true;
5219 add_msg( _( "You take control of the %s." ), veh->name );
5220 } else {
5221 if( !veh->handle_potential_theft( u ) ) {
5222 return;
5223 }
5224 veh->start_engines( true );
5225 }
5226 } else { // Start looking for nearby vehicle controls.
5227 int num_valid_controls = 0;
5228 std::optional<tripoint> vehicle_position;
5229 std::optional<vpart_reference> vehicle_controls;
5230 for( const tripoint elem : m.points_in_radius( g->u.pos(), 1 ) ) {
5231 if( const optional_vpart_position vp = m.veh_at( elem ) ) {
5232 const std::optional<vpart_reference> controls = vp.value().part_with_feature( "CONTROLS", true );
5233 if( controls ) {
5234 num_valid_controls++;
5235 vehicle_position = elem;
5236 vehicle_controls = controls;
5237 }
5238 }
5239 }
5240 if( num_valid_controls < 1 ) {
5241 add_msg( _( "No vehicle controls found." ) );
5242 return;
5243 } else if( num_valid_controls > 1 ) {
5244 vehicle_position = choose_adjacent( _( "Control vehicle where?" ) );
5245 if( !vehicle_position ) {
5246 return;
5247 }
5248 const optional_vpart_position vp = m.veh_at( *vehicle_position );
5249 if( vp ) {
5250 vehicle_controls = vp.value().part_with_feature( "CONTROLS", true );
5251 if( !vehicle_controls ) {
5252 add_msg( _( "The vehicle doesn't have controls there." ) );
5253 return;
5254 }
5255 } else {
5256 add_msg( _( "No vehicle there." ) );
5257 return;
5258 }
5259 }
5260 // If we hit neither of those, there's only one set of vehicle controls, which should already have been found.
5261 if( vehicle_controls ) {
5262 veh = &vehicle_controls->vehicle();
5263 if( !veh->handle_potential_theft( u ) ) {
5264 return;
5265 }
5266 veh->use_controls( *vehicle_position );
5267 //May be folded up (destroyed), so need to re-get it
5268 veh = g->remoteveh();
5269 }
5270 }
5271 if( veh ) {
5272 // If we reached here, we gained control of a vehicle.
5273 // Clear the map memory for the area covered by the vehicle to eliminate ghost vehicles.
5274 for( const tripoint &target : veh->get_points() ) {
5275 u.clear_memorized_tile( m.getabs( target ) );
5276 }
5277 veh->is_following = false;
5278 veh->is_patrolling = false;
5279 veh->autopilot_on = false;
5280 veh->is_autodriving = false;
5281 }
5282}
std::optional< tripoint > choose_adjacent(const std::string &message, const bool allow_vertical)
Request player input of adjacent tile, possibly including vertical tiles.
Definition: action.cpp:988
bool in_vehicle
Definition: character.h:1573
void clear_memorized_tile(const tripoint &pos)
Definition: avatar.cpp:169
vehicle * remoteveh()
Returns the current remotely controlled vehicle.
Definition: game.cpp:2251
tripoint_range< tripoint > points_in_radius(const tripoint &center, size_t radius, size_t radiusz=0) const
Definition: map.cpp:8762
optional_vpart_position veh_at(const tripoint &p) const
Checks if tile is occupied by vehicle and by which part.
Definition: map.cpp:1074
Simple wrapper to forward functions that may return a std::optional to vpart_position.
std::optional< vpart_reference > part_with_feature(const std::string &f, bool unbroken) const
Definition: vehicle.cpp:2483
bool engine_on
Definition: vehicle.h:1721
std::set< tripoint > & get_points(bool force_refresh=false)
Definition: vehicle.cpp:6783
std::string name
Definition: vehicle.h:1581
bool has_engine_type(const itype_id &ft, bool enabled) const
Definition: vehicle.cpp:1033
void start_engines(bool take_control=false, bool autodrive=false)
void use_controls(const tripoint &pos)
Operate vehicle controls.
vehicle(const vproto_id &type_id, int init_veh_fuel=-1, int init_veh_status=-1)
Definition: vehicle.cpp:253
bool has_harnessed_animal() const
bool interact_vehicle_locked()
int avail_part_with_feature(int p, const std::string &f, bool unbroken) const
Definition: vehicle.cpp:2547
bool autopilot_on
Definition: vehicle.h:1729
bool is_autodriving
Definition: vehicle.h:1714
bool handle_potential_theft(avatar &you, bool check_only=false, bool prompt=true)
Handle potential vehicle theft.
Definition: vehicle.cpp:4409
static const trait_id trait_WAYFARER("WAYFARER")

References _, add_msg(), vehicle::autopilot_on, vehicle::avail_part_with_feature(), choose_adjacent(), avatar::clear_memorized_tile(), Character::controlling_vehicle, vehicle::engine_on, fuel_type_animal, g, vehicle::get_points(), map::getabs(), vehicle::handle_potential_theft(), vehicle::has_engine_type(), vehicle::has_harnessed_animal(), Character::has_trait(), Character::in_vehicle, vehicle::interact_vehicle_locked(), vehicle::is_autodriving, vehicle::is_following, vehicle::is_patrolling, m, m_info, vehicle::name, optional_vpart_position::part_with_feature(), vehicle::player_in_control(), map::points_in_radius(), Character::pos(), remoteveh(), vehicle::start_engines(), trait_WAYFARER, u, vehicle::use_controls(), map::veh_at(), and vehicle::vehicle().

Referenced by handle_action().

◆ create_or_get_main_ui_adaptor()

shared_ptr_fast< ui_adaptor > game::create_or_get_main_ui_adaptor ( )

In tiles mode w_terrain can have a different font (with a different tile dimension) or can be drawn by cata_tiles which uses tiles that again might have a different dimension then the normal font used everywhere else.

TERRAIN_WINDOW_WIDTH/TERRAIN_WINDOW_HEIGHT defines how many squares can be displayed in w_terrain (using it's specific tile dimension), not including partially drawn squares at the right/bottom. You should use it whenever you want to draw specific squares in that window or to determine whether a specific square is draw on screen (or outside the screen and needs scrolling).

TERRAIN_WINDOW_TERM_WIDTH/TERRAIN_WINDOW_TERM_HEIGHT defines the size of w_terrain in the standard font dimension (the font that everything else uses). You usually don't have to use it, expect for positioning of windows, because the window positions use the standard font dimension.

The code here calculates size available for w_terrain, caps it at max_view_size (the maximal view range than any character can have at any time). It is stored in TERRAIN_WINDOW_*.

Definition at line 2927 of file game.cpp.

2928{
2930 if( !ui ) {
2931 main_ui_adaptor = ui = make_shared_fast<ui_adaptor>();
2932 ui->on_redraw( []( const ui_adaptor & ) {
2933 g->draw();
2934 } );
2935 ui->on_screen_resize( [this]( ui_adaptor & ui ) {
2936 // remove some space for the sidebar, this is the maximal space
2937 // (using standard font) that the terrain window can have
2938 const int sidebar_left = panel_manager::get_manager().get_width_left();
2939 const int sidebar_right = panel_manager::get_manager().get_width_right();
2940
2942 TERRAIN_WINDOW_WIDTH = TERMX - ( sidebar_left + sidebar_right );
2945
2946 /**
2947 * In tiles mode w_terrain can have a different font (with a different
2948 * tile dimension) or can be drawn by cata_tiles which uses tiles that again
2949 * might have a different dimension then the normal font used everywhere else.
2950 *
2951 * TERRAIN_WINDOW_WIDTH/TERRAIN_WINDOW_HEIGHT defines how many squares can
2952 * be displayed in w_terrain (using it's specific tile dimension), not
2953 * including partially drawn squares at the right/bottom. You should
2954 * use it whenever you want to draw specific squares in that window or to
2955 * determine whether a specific square is draw on screen (or outside the screen
2956 * and needs scrolling).
2957 *
2958 * TERRAIN_WINDOW_TERM_WIDTH/TERRAIN_WINDOW_TERM_HEIGHT defines the size of
2959 * w_terrain in the standard font dimension (the font that everything else uses).
2960 * You usually don't have to use it, expect for positioning of windows,
2961 * because the window positions use the standard font dimension.
2962 *
2963 * The code here calculates size available for w_terrain, caps it at
2964 * max_view_size (the maximal view range than any character can have at
2965 * any time).
2966 * It is stored in TERRAIN_WINDOW_*.
2967 */
2969
2970 // Position of the player in the terrain window, it is always in the center
2973
2975 point( sidebar_left, 0 ) );
2976
2977 // minimap is always MINIMAP_WIDTH x MINIMAP_HEIGHT in size
2979
2980 // need to init in order to avoid crash. gets updated by the panel code.
2982
2983 ui.position_from_window( catacurses::stdscr );
2984 } );
2985 ui->mark_resize();
2986 }
2987 return ui;
2988}
catacurses::window w_pixel_minimap
Definition: game.h:990
catacurses::window w_minimap_ptr
Definition: game.h:1027
weak_ptr_fast< ui_adaptor > main_ui_adaptor
Definition: game.h:1073
catacurses::window w_minimap
Definition: game.h:989
catacurses::window w_terrain_ptr
Definition: game.h:1026
static panel_manager & get_manager()
Definition: panels.h:72
int get_width_right()
Definition: panels.cpp:2187
int get_width_left()
Definition: panels.cpp:2195
Adaptor between UI code and the UI management system.
Definition: ui_manager.h:65
static constexpr int MINIMAP_WIDTH
static constexpr int MINIMAP_HEIGHT
void to_map_font_dimension(int &, int &)
Definition: game_ui.cpp:20
std::shared_ptr< T > shared_ptr_fast
Definition: memory_fast.h:16
window stdscr
Definition: overmap_ui.h:17
int TERRAIN_WINDOW_TERM_WIDTH
Definition: output.cpp:53
int TERRAIN_WINDOW_TERM_HEIGHT
Definition: output.cpp:54
int POSX
Definition: output.cpp:49
int TERRAIN_WINDOW_WIDTH
Definition: output.cpp:51
int POSY
Definition: output.cpp:50
int TERRAIN_WINDOW_HEIGHT
Definition: output.cpp:52

References g, panel_manager::get_manager(), panel_manager::get_width_left(), panel_manager::get_width_right(), main_ui_adaptor, MINIMAP_HEIGHT, MINIMAP_WIDTH, catacurses::newwin(), point_zero, POSX, POSY, catacurses::stdscr, TERMX, TERMY, TERRAIN_WINDOW_HEIGHT, TERRAIN_WINDOW_TERM_HEIGHT, TERRAIN_WINDOW_TERM_WIDTH, TERRAIN_WINDOW_WIDTH, to_map_font_dimension(), w_minimap, w_minimap_ptr, w_pixel_minimap, w_terrain, and w_terrain_ptr.

◆ create_starting_npcs()

void game::create_starting_npcs ( )
private

Definition at line 888 of file game.cpp.

889{
890 if( !get_option<bool>( "STATIC_NPC" ) ||
891 get_option<std::string>( "STARTING_NPC" ) == "never" ) {
892 return; //Do not generate a starting npc.
893 }
894
895 //We don't want more than one starting npc per starting location
896 const int radius = 1;
897 if( !overmap_buffer.get_npcs_near_player( radius ).empty() ) {
898 return; //There is already an NPC in this starting location
899 }
900
901 shared_ptr_fast<npc> tmp = make_shared_fast<npc>();
902 tmp->randomize( one_in( 2 ) ? NC_DOCTOR : NC_NONE );
903 tmp->spawn_at_precise( { get_levx(), get_levy() }, u.pos() - point_south_east );
905 tmp->form_opinion( u );
906 tmp->set_attitude( NPCATT_NULL );
907 //This sets the NPC mission. This NPC remains in the starting location.
908 tmp->mission = NPC_MISSION_SHELTER;
909 tmp->chatbin.first_topic = "TALK_SHELTER";
910 tmp->toggle_trait( trait_id( "NPC_STARTING_NPC" ) );
911 tmp->set_fac( faction_id( "no_faction" ) );
912 //One random starting NPC mission
913 tmp->add_new_mission( mission::reserve_random( ORIGIN_OPENER_NPC, tmp->global_omt_location(),
914 tmp->getID() ) );
915}
int get_levy() const
Definition: game.cpp:11932
int get_levx() const
The top left corner of the reality bubble (in submaps coordinates).
Definition: game.cpp:11927
static mission * reserve_random(mission_origin origin, const tripoint_abs_omt &p, const character_id &npc_id)
Definition: mission.cpp:200
std::vector< shared_ptr_fast< npc > > get_npcs_near_player(int radius)
Same as get_npcs_near(int,int,int,int) but uses player position as center.
void insert_npc(const shared_ptr_fast< npc > &who)
Adds the npc to an overmap ( based on the npcs current location ) and stores it there.
string_id< faction > faction_id
Definition: clzones.h:30
@ ORIGIN_OPENER_NPC
Definition: mission.h:45
@ NPCATT_NULL
Definition: npc.h:81
@ NPC_MISSION_SHELTER
Definition: npc.h:144
npc_class_id NC_NONE("NC_NONE")
npc_class_id NC_DOCTOR("NC_DOCTOR")
static constexpr point point_south_east
Definition: point.h:265
bool one_in(int chance)
Definition: rng.cpp:65

References get_levx(), get_levy(), overmapbuffer::get_npcs_near_player(), overmapbuffer::insert_npc(), NC_DOCTOR, NC_NONE, NPC_MISSION_SHELTER, NPCATT_NULL, one_in(), ORIGIN_OPENER_NPC, overmap_buffer, point_south_east, Character::pos(), mission::reserve_random(), trait_id, and u.

Referenced by start_game().

◆ critter_at() [1/2]

template<typename T >
T * game::critter_at ( const tripoint p,
bool  allow_hallucination = false 
)

Returns the Creature at the given location.

Optionally casted to the given type of creature: npc, player, monster - if there is a creature, but it's not of the requested type, returns nullptr.

Parameters
allow_hallucinationWhether to return monsters that are actually hallucinations.

Definition at line 4545 of file game.cpp.

4546{
4547 if( const shared_ptr_fast<monster> mon_ptr = critter_tracker->find( p ) ) {
4548 if( !allow_hallucination && mon_ptr->is_hallucination() ) {
4549 return nullptr;
4550 }
4551 // if we wanted to check for an NPC / player / avatar,
4552 // there is sometimes a monster AND an NPC/player there at the same time.
4553 // because the NPC/player etc may be riding that monster.
4554 // so only return the monster if we were actually looking for a monster.
4555 // otherwise, keep looking for the rider.
4556 // critter_at<creature> or critter_at() with no template will still default to returning monster first,
4557 // which is ok for the occasions where that happens.
4558 if( !mon_ptr->has_effect( effect_ridden ) || ( std::is_same<T, monster>::value ||
4559 std::is_same<T, Creature>::value || std::is_same<T, const monster>::value ||
4560 std::is_same<T, const Creature>::value ) ) {
4561 return dynamic_cast<T *>( mon_ptr.get() );
4562 }
4563 }
4564 if( !std::is_same<T, npc>::value && !std::is_same<T, const npc>::value ) {
4565 if( p == u.pos() ) {
4566 return dynamic_cast<T *>( &u );
4567 }
4568 }
4569 for( auto &cur_npc : active_npc ) {
4570 if( cur_npc->pos() == p && !cur_npc->is_dead() ) {
4571 return dynamic_cast<T *>( cur_npc.get() );
4572 }
4573 }
4574 return nullptr;
4575}
static const efftype_id effect_ridden("ridden")

References active_npc, critter_tracker, effect_ridden, Character::pos(), and u.

Referenced by draw_look_around_cursor(), examine(), find_or_make_stairs(), fling_creature(), forced_door_closing(), get_player_input(), is_empty(), knockback(), phasing_move(), print_all_tile_info(), spawn_hallucination(), swap_critters(), and update_stair_monsters().

◆ critter_at() [2/2]

template<typename T >
const T * game::critter_at ( const tripoint p,
bool  allow_hallucination = false 
) const

Definition at line 4578 of file game.cpp.

4579{
4580 return const_cast<game *>( this )->critter_at<T>( p, allow_hallucination );
4581}
Definition: game.h:144

◆ critter_by_id()

template<typename T >
template Creature * game::critter_by_id< Creature > ( const character_id id)
Returns
The living creature with the given id. Returns null if no living creature with such an id exists. Never returns a dead creature. Currently only the player character and npcs have ids.

Definition at line 4624 of file game.cpp.

4625{
4626 if( id == u.getID() ) {
4627 // player is always alive, therefore no is-dead check
4628 return dynamic_cast<T *>( &u );
4629 }
4630 return find_npc( id );
4631}
character_id getID() const
Definition: character.cpp:495
npc * find_npc(character_id id)
Find the npc with the given ID.
Definition: game.cpp:1870

References find_npc(), Character::getID(), and u.

◆ death_screen()

void game::death_screen ( )
private

Definition at line 2421 of file game.cpp.

2422{
2423 gamemode->game_over();
2428 follower_ids.clear();
2430}
diary * get_avatar_diary()
Definition: avatar.cpp:370
void death_entry()
Definition: diary.cpp:672
stats_tracker & stats()
Definition: game.cpp:2719
void disp_NPC_epilogues()
Definition: game.cpp:2814
void display_faction_epilogues()
Definition: game.cpp:2831
void display_messages()
Definition: messages.cpp:827
void show_scores_ui(const achievements_tracker &achievements, stats_tracker &stats, const kill_tracker &kills)
Definition: scores_ui.cpp:69

References achievements_tracker_ptr, diary::death_entry(), disp_NPC_epilogues(), display_faction_epilogues(), Messages::display_messages(), follower_ids, gamemode, avatar::get_avatar_diary(), get_kill_tracker(), show_scores_ui(), stats(), and u.

Referenced by cleanup_at_end().

◆ despawn_monster()

void game::despawn_monster ( monster critter)

Despawn a specific monster, it's stored on the overmap.

Also removes it from the creature tracker. Keep in mind that any monster index may point to a different monster after calling this (or to no monster at all).

Definition at line 11051 of file game.cpp.

11052{
11053 if( !critter.is_hallucination() ) {
11054 // hallucinations aren't stored, they come and go as they like,
11056 }
11057
11058 critter.on_unload();
11059 remove_zombie( critter );
11060 // simulate it being dead so further processing of it (e.g. in monmove) will yield
11061 critter.set_hp( 0 );
11062}
void remove_zombie(const monster &critter)
Definition: game.cpp:4735
bool is_hallucination() const override
Definition: monster.cpp:2715
void on_unload()
Do some cleanup and caching as monster is being unloaded from map.
Definition: monster.cpp:3051
void set_hp(int hp)
Directly set the current hp of the monster (not capped at the maximal hp).
Definition: monster.cpp:1686
void despawn_monster(const monster &critter)
Despawn the monster back onto the overmap.

References overmapbuffer::despawn_monster(), monster::is_hallucination(), monster::on_unload(), overmap_buffer, remove_zombie(), and monster::set_hp().

Referenced by cleanup_at_end(), monmove(), place_player_overmap(), and shift_monsters().

◆ disable_robot()

bool game::disable_robot ( const tripoint p)

If there is a robot (that can be disabled), query the player and try to disable it.

Returns
true if the robot has been disabled or a similar action has been done. false if the player did not choose any action and the function has effectively done nothing.

Definition at line 8658 of file game.cpp.

8659{
8660 monster *const mon_ptr = critter_at<monster>( p );
8661 if( !mon_ptr ) {
8662 return false;
8663 }
8664 monster &critter = *mon_ptr;
8665 if( critter.friendly == 0 || critter.has_effect( effect_pet ) ||
8666 critter.has_flag( MF_RIDEABLE_MECH ) ||
8667 ( critter.has_flag( MF_PAY_BOT ) && critter.has_effect( effect_paid ) ) ) {
8668 // Can only disable / reprogram friendly monsters
8669 return false;
8670 }
8671 const auto mid = critter.type->id;
8672 const auto mon_item_id = critter.type->revert_to_itype;
8673 if( !mon_item_id.is_empty() &&
8674 query_yn( _( "Deactivate the %s?" ), critter.name() ) ) {
8675
8676 u.moves -= 100;
8677 m.add_item_or_charges( p, critter.to_item() );
8678 if( !critter.has_flag( MF_INTERIOR_AMMO ) ) {
8679 for( auto &ammodef : critter.ammo ) {
8680 if( ammodef.second > 0 ) {
8681 m.spawn_item( p.xy(), ammodef.first, 1, ammodef.second, calendar::turn );
8682 }
8683 }
8684 }
8685 remove_zombie( critter );
8686 return true;
8687 }
8688 // Manhacks are special, they have their own menu here.
8689 if( mid == mon_manhack ) {
8690 int choice = UILIST_CANCEL;
8691 if( critter.has_effect( effect_docile ) ) {
8692 choice = uilist( _( "Reprogram the manhack?" ), { _( "Engage targets." ) } );
8693 } else {
8694 choice = uilist( _( "Reprogram the manhack?" ), { _( "Follow me." ) } );
8695 }
8696 switch( choice ) {
8697 case 0:
8698 if( critter.has_effect( effect_docile ) ) {
8699 critter.remove_effect( effect_docile );
8700 if( one_in( 3 ) ) {
8701 add_msg( _( "The %s hovers momentarily as it surveys the area." ),
8702 critter.name() );
8703 }
8704 } else {
8705 critter.add_effect( effect_docile, 1_turns, num_bp );
8706 if( one_in( 3 ) ) {
8707 add_msg( _( "The %s lets out a whirring noise and starts to follow you." ),
8708 critter.name() );
8709 }
8710 }
8711 u.moves -= 100;
8712 return true;
8713 default:
8714 break;
8715 }
8716 }
8717 return false;
8718}
@ num_bp
Definition: bodypart.h:54
bool remove_effect(const efftype_id &eff_id, body_part bp=num_bp)
Removes a listed effect.
Definition: creature.cpp:1164
void spawn_item(const tripoint &p, const itype_id &type_id, unsigned quantity=1, int charges=0, const time_point &birthday=calendar::start_of_cataclysm, int damlevel=0)
Definition: map.cpp:4314
bool has_flag(m_flag f) const override
Definition: monster.cpp:894
item to_item() const
Convert this monster into an item (see mtype::revert_to_itype).
Definition: monster.cpp:2855
void add_effect(const efftype_id &eff_id, const time_duration &dur, const bodypart_str_id &bp, int intensity=0, bool force=false, bool deferred=false) override
Performs any monster-specific modifications to the arguments before passing to Creature::add_effect()...
Definition: monster.cpp:1862
int friendly
Definition: monster.h:471
std::string name(unsigned int quantity=1) const
Definition: monster.cpp:489
std::map< itype_id, int > ammo
Definition: monster.h:512
static const efftype_id effect_pet("pet")
static const efftype_id effect_docile("docile")
static const efftype_id effect_paid("paid")
static const mtype_id mon_manhack("mon_manhack")
@ MF_INTERIOR_AMMO
Definition: mtype.h:146
@ MF_RIDEABLE_MECH
Definition: mtype.h:115
@ MF_PAY_BOT
Definition: mtype.h:121
itype_id revert_to_itype
If this is not empty, the monster can be converted into an item of this type (if it's friendly).
Definition: mtype.h:364
constexpr point xy() const
Definition: point.h:206
const int UILIST_CANCEL
Definition: ui.h:28

References _, monster::add_effect(), map::add_item_or_charges(), add_msg(), monster::ammo, effect_docile, effect_paid, effect_pet, monster::friendly, Creature::has_effect(), monster::has_flag(), mtype::id, m, MF_INTERIOR_AMMO, MF_PAY_BOT, MF_RIDEABLE_MECH, mon_manhack, Creature::moves, monster::name(), num_bp, one_in(), query_yn(), Creature::remove_effect(), remove_zombie(), mtype::revert_to_itype, map::spawn_item(), monster::to_item(), calendar::turn, monster::type, u, UILIST_CANCEL, and tripoint::xy().

Referenced by examine().

◆ disp_NPC_epilogues()

void game::disp_NPC_epilogues ( )
private

Definition at line 2814 of file game.cpp.

2815{
2816 // TODO: This search needs to be expanded to all NPCs
2817 for( auto elem : follower_ids ) {
2819 if( !guy ) {
2820 continue;
2821 }
2822 const auto new_win = []() {
2824 point( std::max( 0, ( TERMX - FULL_SCREEN_WIDTH ) / 2 ),
2825 std::max( 0, ( TERMY - FULL_SCREEN_HEIGHT ) / 2 ) ) );
2826 };
2827 scrollable_text( new_win, guy->disp_name(), guy->get_epilogue() );
2828 }
2829}
shared_ptr_fast< npc > find_npc(character_id id)
Find the npc with the given ID.
void scrollable_text(const std::function< catacurses::window()> &init_window, const std::string &title, const std::string &text)
Definition: output.cpp:352

References overmapbuffer::find_npc(), follower_ids, FULL_SCREEN_HEIGHT, FULL_SCREEN_WIDTH, catacurses::newwin(), overmap_buffer, scrollable_text(), TERMX, and TERMY.

Referenced by death_screen().

◆ disp_NPCs()

void game::disp_NPCs ( )

Definition at line 2865 of file game.cpp.

2866{
2867 const tripoint_abs_omt ppos = u.global_omt_location();
2868 const tripoint &lpos = u.pos();
2869 std::vector<shared_ptr_fast<npc>> npcs = overmap_buffer.get_npcs_near_player( 100 );
2870 std::sort( npcs.begin(), npcs.end(), npc_dist_to_player() );
2871
2873 ui_adaptor ui;
2874 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
2877 TERMY > FULL_SCREEN_HEIGHT ? ( TERMY - FULL_SCREEN_HEIGHT ) / 2 : 0 ) );
2878 ui.position_from_window( w );
2879 } );
2880 ui.mark_resize();
2881 ui.on_redraw( [&]( const ui_adaptor & ) {
2882 werase( w );
2883 mvwprintz( w, point_zero, c_white, _( "Your overmap position: %s" ), ppos.to_string() );
2884 // NOLINTNEXTLINE(cata-use-named-point-constants)
2885 mvwprintz( w, point( 0, 1 ), c_white, _( "Your local position: %s" ), lpos.to_string() );
2886 size_t i;
2887 for( i = 0; i < 20 && i < npcs.size(); i++ ) {
2888 const tripoint_abs_omt apos = npcs[i]->global_omt_location();
2889 mvwprintz( w, point( 0, i + 3 ), c_white, "%s: %s", npcs[i]->name,
2890 apos.to_string() );
2891 }
2892 for( const monster &m : all_monsters() ) {
2893 mvwprintz( w, point( 0, i + 3 ), c_white, "%s: %d, %d, %d", m.name(),
2894 m.posx(), m.posy(), m.posz() );
2895 ++i;
2896 }
2897 wnoutrefresh( w );
2898 } );
2899
2900 input_context ctxt( "DISP_NPCS" );
2901 ctxt.register_action( "CONFIRM" );
2902 ctxt.register_action( "QUIT" );
2903 ctxt.register_action( "HELP_KEYBINDINGS" );
2904 bool stop = false;
2905 while( !stop ) {
2907 const std::string action = ctxt.handle_input();
2908 if( action == "CONFIRM" || action == "QUIT" ) {
2909 stop = true;
2910 }
2911 }
2912}
tripoint_abs_omt global_omt_location() const
Returns the location of the player in global overmap terrain coordinates.
Definition: character.cpp:6269
std::string to_string() const
Definition: coordinates.h:140
Represents a context in which a set of actions can be performed.
Definition: input.h:382
std::string name(const tripoint &p)
Definition: map.cpp:1390
void wnoutrefresh(const window &win)
Definition: ncurses_def.cpp:43
void werase(const window &win)
Definition: ncurses_def.cpp:53
std::string to_string() const
Definition: point.cpp:34

References _, action, all_monsters(), c_white, FULL_SCREEN_HEIGHT, FULL_SCREEN_WIDTH, overmapbuffer::get_npcs_near_player(), Character::global_omt_location(), input_context::handle_input(), m, mvwprintz(), map::name(), om_direction::name(), catacurses::newwin(), overmap_buffer, point_zero, Character::pos(), ui_manager::redraw(), input_context::register_action(), TERMX, TERMY, coords::coord_point< Point, Origin, Scale >::to_string(), tripoint::to_string(), u, catacurses::werase(), and catacurses::wnoutrefresh().

◆ display_faction_epilogues()

void game::display_faction_epilogues ( )
private

Definition at line 2831 of file game.cpp.

2832{
2833 for( const auto &elem : faction_manager_ptr->all() ) {
2834 if( elem.second.known_by_u ) {
2835 const std::vector<std::string> epilogue = elem.second.epilogue();
2836 if( !epilogue.empty() ) {
2837 const auto new_win = []() {
2839 point( std::max( 0, ( TERMX - FULL_SCREEN_WIDTH ) / 2 ),
2840 std::max( 0, ( TERMY - FULL_SCREEN_HEIGHT ) / 2 ) ) );
2841 };
2842 scrollable_text( new_win, elem.second.name,
2843 std::accumulate( epilogue.begin() + 1, epilogue.end(), epilogue.front(),
2844 []( const std::string & lhs, const std::string & rhs ) -> std::string {
2845 return lhs + "\n" + rhs;
2846 } ) );
2847 }
2848 }
2849 }
2850}
pimpl< faction_manager > faction_manager_ptr
Definition: game.h:973

References faction_manager_ptr, FULL_SCREEN_HEIGHT, FULL_SCREEN_WIDTH, catacurses::newwin(), scrollable_text(), TERMX, and TERMY.

Referenced by death_screen().

◆ display_lighting()

void game::display_lighting ( )
private

Definition at line 11277 of file game.cpp.

11278{
11279 if( use_tiles ) {
11281 if( !g->display_overlay_state( ACTION_DISPLAY_LIGHTING ) ) {
11282 return;
11283 }
11284 uilist lighting_menu;
11285 std::vector<std::string> lighting_menu_strings{
11286 "Global lighting conditions"
11287 };
11288
11289 int count = 0;
11290 for( const auto &menu_str : lighting_menu_strings ) {
11291 lighting_menu.addentry( count++, true, MENU_AUTOASSIGN, "%s", menu_str );
11292 }
11293
11294 lighting_menu.w_y_setup = 0;
11295 lighting_menu.query();
11296 if( ( lighting_menu.ret >= 0 ) &&
11297 ( static_cast<size_t>( lighting_menu.ret ) < lighting_menu_strings.size() ) ) {
11298 g->displaying_lighting_condition = lighting_menu.ret;
11299 }
11300 }
11301}
@ ACTION_DISPLAY_LIGHTING
Toggle lighting conditions map.
Definition: action.h:321
bool use_tiles
Use tiles for display.
void display_toggle_overlay(action_id)
Definition: game.cpp:11173
pos_scalar w_y_setup
Definition: ui.h:338
constexpr size_t count()
Definition: fmtlib_core.h:1073
const int MENU_AUTOASSIGN
Definition: ui.h:31

References ACTION_DISPLAY_LIGHTING, uilist::addentry(), detail::count(), display_toggle_overlay(), g, MENU_AUTOASSIGN, uilist::query(), uilist::ret, use_tiles, and uilist::w_y_setup.

Referenced by handle_action(), and look_around().

◆ display_overlay_state()

bool game::display_overlay_state ( action_id  action)

Definition at line 11168 of file game.cpp.

11169{
11171}
std::optional< action_id > displaying_overlays
Definition: game.h:917

References action, and displaying_overlays.

Referenced by display_toggle_overlay(), and display_visibility().

◆ display_radiation()

void game::display_radiation ( )
private

Definition at line 11303 of file game.cpp.

11304{
11305 if( use_tiles ) {
11307 }
11308}
@ ACTION_DISPLAY_RADIATION
Toggle radiation map.
Definition: action.h:323

References ACTION_DISPLAY_RADIATION, display_toggle_overlay(), and use_tiles.

Referenced by handle_action(), and look_around().

◆ display_scent()

void game::display_scent ( )
private

Definition at line 11182 of file game.cpp.

11183{
11184 if( use_tiles ) {
11186 } else {
11187 int div;
11188 bool got_value = query_int( div, _( "Set the Scent Map sensitivity to (0 to cancel)?" ) );
11189 if( !got_value || div < 1 ) {
11190 add_msg( _( "Never mind." ) );
11191 return;
11192 }
11193 shared_ptr_fast<game::draw_callback_t> scent_cb = make_shared_fast<game::draw_callback_t>( [&]() {
11194 scent.draw( w_terrain, div * 2, u.pos() + u.view_offset );
11195 } );
11196 g->add_draw_callback( scent_cb );
11197
11200 }
11201}
@ ACTION_DISPLAY_SCENT
Toggle scent map.
Definition: action.h:283
void wait_for_any_key()
Wait until the user presses a key.
Definition: input.cpp:1303
tripoint view_offset
Definition: player.h:233
void draw(const catacurses::window &win, int div, const tripoint &center) const
Definition: scent_map.cpp:70
input_manager inp_mngr
Definition: input.cpp:109
bool query_int(int &result, int default_val, const std::string &text)
Definition: output.cpp:718

References _, ACTION_DISPLAY_SCENT, add_msg(), display_toggle_overlay(), scent_map::draw(), g, inp_mngr, Character::pos(), query_int(), ui_manager::redraw(), scent, u, use_tiles, player::view_offset, w_terrain, and input_manager::wait_for_any_key().

Referenced by handle_action(), and look_around().

◆ display_temperature()

void game::display_temperature ( )
private

Definition at line 11203 of file game.cpp.

11204{
11205 if( use_tiles ) {
11207 }
11208}
@ ACTION_DISPLAY_TEMPERATURE
Toggle temperature map.
Definition: action.h:315

References ACTION_DISPLAY_TEMPERATURE, display_toggle_overlay(), and use_tiles.

Referenced by handle_action(), and look_around().

◆ display_toggle_overlay()

void game::display_toggle_overlay ( action_id  action)

Definition at line 11173 of file game.cpp.

11174{
11175 if( display_overlay_state( action ) ) {
11176 displaying_overlays.reset();
11177 } else {
11179 }
11180}
bool display_overlay_state(action_id)
Definition: game.cpp:11168

References action, display_overlay_state(), and displaying_overlays.

Referenced by display_lighting(), display_radiation(), display_scent(), display_temperature(), display_transparency(), display_vehicle_ai(), and display_visibility().

◆ display_transparency()

void game::display_transparency ( )
private

Definition at line 11310 of file game.cpp.

11311{
11312 if( use_tiles ) {
11314 }
11315}
@ ACTION_DISPLAY_TRANSPARENCY
Toggle transparency map.
Definition: action.h:325

References ACTION_DISPLAY_TRANSPARENCY, display_toggle_overlay(), and use_tiles.

Referenced by handle_action(), and look_around().

◆ display_vehicle_ai()

void game::display_vehicle_ai ( )
private

Definition at line 11210 of file game.cpp.

11211{
11212 if( use_tiles ) {
11214 }
11215}
@ ACTION_DISPLAY_VEHICLE_AI
Toggle vehicle autopilot data.
Definition: action.h:317

References ACTION_DISPLAY_VEHICLE_AI, display_toggle_overlay(), and use_tiles.

Referenced by handle_action().

◆ display_visibility()

void game::display_visibility ( )
private

Definition at line 11217 of file game.cpp.

11218{
11219 if( use_tiles ) {
11222 std::vector< tripoint > locations;
11223 uilist creature_menu;
11224 int num_creatures = 0;
11225 creature_menu.addentry( num_creatures++, true, MENU_AUTOASSIGN, "%s", _( "You" ) );
11226 locations.emplace_back( g->u.pos() ); // add player first.
11227 for( const Creature &critter : g->all_creatures() ) {
11228 if( critter.is_player() ) {
11229 continue;
11230 }
11231 creature_menu.addentry( num_creatures++, true, MENU_AUTOASSIGN, critter.disp_name() );
11232 locations.emplace_back( critter.pos() );
11233 }
11234
11235 pointmenu_cb callback( locations );
11236 creature_menu.callback = &callback;
11237 creature_menu.w_y_setup = 0;
11238 creature_menu.query();
11239 if( creature_menu.ret >= 0 && static_cast<size_t>( creature_menu.ret ) < locations.size() ) {
11240 Creature *creature = critter_at<Creature>( locations[creature_menu.ret] );
11242 }
11243 } else {
11245 }
11246 }
11247}
@ ACTION_DISPLAY_VISIBILITY
Toggle visibility map.
Definition: action.h:319
size_t num_creatures() const
Returns the approximate number of creatures in the reality bubble.
Definition: game.cpp:4725
Creature * displaying_visibility_creature
Creature for which to display the visibility map.
Definition: game.h:1009
Callback for uilist that pairs menu entries with points When an entry is selected,...
Definition: ui.h:423
uilist_callback * callback
Definition: ui.h:335
generic_factory< overmap_location > locations("overmap location")

References _, ACTION_DISPLAY_VISIBILITY, uilist::addentry(), uilist::callback, creature, display_overlay_state(), display_toggle_overlay(), displaying_visibility_creature, g, anonymous_namespace{overmap_location.cpp}::locations, MENU_AUTOASSIGN, num_creatures(), uilist::query(), uilist::ret, use_tiles, and uilist::w_y_setup.

Referenced by handle_action().

◆ do_turn()

bool game::do_turn ( )

MAIN GAME LOOP.

Returns true if game is over (death, saved, quit, etc.).

Definition at line 1350 of file game.cpp.

1351{
1352 if( is_game_over() ) {
1353 return cleanup_at_end();
1354 }
1355 // Actual stuff
1356 if( new_game ) {
1357 new_game = false;
1358 } else {
1359 gamemode->per_turn();
1360 calendar::turn += 1_turns;
1361 }
1362
1363 // starting a new turn, clear out temperature cache
1365 weather.clear_temp_cache();
1366
1367 if( npcs_dirty ) {
1368 load_npcs();
1369 }
1370
1373 // If controlling a vehicle that is owned by someone else
1375 vehicle *veh = veh_pointer_or_null( m.veh_at( u.pos() ) );
1376 if( veh && !veh->handle_potential_theft( u, true ) ) {
1377 veh->handle_potential_theft( u, false, false );
1378 }
1379 }
1380 // If riding a horse - chance to spook
1381 if( u.is_mounted() ) {
1383 }
1384 if( calendar::once_every( 1_days ) ) {
1386 }
1387
1388 // Move hordes every 2.5 min
1391 // Hordes that reached the reality bubble need to spawn,
1392 // make them spawn in invisible areas only.
1393 m.spawn_monsters( false );
1394 }
1395
1397
1398 u.update_body();
1399
1400 // Auto-save if autosave is enabled
1401 if( get_option<bool>( "AUTOSAVE" ) &&
1402 calendar::once_every( 1_turns * get_option<int>( "AUTOSAVE_TURNS" ) ) &&
1403 !u.is_dead_state() ) {
1404 autosave();
1405 }
1406
1407 weather.update_weather();
1409
1413 // Process NPC sound events before they move or they hear themselves talking
1414 for( npc &guy : all_npcs() ) {
1415 if( rl_dist( guy.pos(), u.pos() ) < MAX_VIEW_DISTANCE ) {
1417 }
1418 }
1419
1420 // Process sound events into sound markers for display to the player.
1422
1423 if( u.is_deaf() ) {
1425 }
1426
1427 if( !u.has_effect( effect_sleep ) || uquit == QUIT_WATCH ) {
1428 if( u.moves > 0 || uquit == QUIT_WATCH ) {
1429 while( u.moves > 0 || uquit == QUIT_WATCH ) {
1430 cleanup_dead();
1432 // Process any new sounds the player caused during their turn.
1433 for( npc &guy : all_npcs() ) {
1434 if( rl_dist( guy.pos(), u.pos() ) < MAX_VIEW_DISTANCE ) {
1436 }
1437 }
1440 wait_popup.reset();
1442 }
1443
1444 if( queue_screenshot ) {
1448 queue_screenshot = false;
1449 }
1450
1451 if( handle_action() ) {
1453 u.action_taken();
1454 }
1455
1456 if( is_game_over() ) {
1457 return cleanup_at_end();
1458 }
1459
1460 if( uquit == QUIT_WATCH ) {
1461 break;
1462 }
1463 if( u.activity ) {
1465 }
1466 }
1467 // Reset displayed sound markers now that the turn is over.
1468 // We only want this to happen if the player had a chance to examine the sounds.
1470 }
1471 }
1472
1473 if( driving_view_offset.x != 0 || driving_view_offset.y != 0 ) {
1474 // Still have a view offset, but might not be driving anymore,
1475 // or the option has been deactivated,
1476 // might also happen when someone dives from a moving car.
1477 // or when using the handbrake.
1478 vehicle *veh = veh_pointer_or_null( m.veh_at( u.pos() ) );
1479 calc_driving_offset( veh );
1480 }
1481
1482 // No-scent debug mutation has to be processed here or else it takes time to start working
1483 if( !u.has_active_bionic( bionic_id( "bio_scent_mask" ) ) &&
1484 !u.has_trait( trait_id( "DEBUG_NOSCENT" ) ) ) {
1487 }
1488 scent.update( u.pos(), m );
1489
1490 // We need floor cache before checking falling 'n stuff
1492
1495 m.vehmove();
1496 m.process_fields();
1497 m.process_items();
1500
1501 // Apply sounds from previous turn to monster and NPC AI.
1503 // Update vision caches for monsters. If this turns out to be expensive,
1504 // consider a stripped down cache just for monsters.
1505 m.build_map_cache( get_levz(), true );
1506 monmove();
1507 if( calendar::once_every( 5_minutes ) ) {
1509 }
1510 if( calendar::once_every( 10_seconds ) ) {
1511 for( const tripoint &elem : m.get_furn_field_locations() ) {
1512 const auto &furn = m.furn( elem ).obj();
1513 for( const emit_id &e : furn.emissions ) {
1514 m.emit_field( elem, e );
1515 }
1516 }
1517 }
1520 u.process_turn();
1521
1523
1525 cleanup_dead();
1526
1527 if( u.moves < 0 && get_option<bool>( "FORCE_REDRAW" ) ) {
1530 }
1531
1532 if( get_levz() >= 0 && !u.is_underwater() ) {
1533 handle_weather_effects( weather.weather_id );
1534 }
1535
1536 const bool player_is_sleeping = u.has_effect( effect_sleep );
1537 bool wait_redraw = false;
1538 std::string wait_message;
1539 time_duration wait_refresh_rate;
1540 if( player_is_sleeping ) {
1541 wait_redraw = true;
1542 wait_message = _( "Wait till you wake up…" );
1543 wait_refresh_rate = 30_minutes;
1544 if( calendar::once_every( 1_hours ) ) {
1546 }
1547 } else if( u.has_destination() ) {
1548 wait_redraw = true;
1549 wait_message = _( "Travelling…" );
1550 wait_refresh_rate = 15_turns;
1551 } else if( const std::optional<std::string> progress = u.activity.get_progress_message( u ) ) {
1552 wait_redraw = true;
1553 wait_message = *progress;
1554 if( u.activity.id() == ACT_AUTODRIVE ) {
1555 wait_refresh_rate = 1_turns;
1556 } else {
1557 wait_refresh_rate = 5_minutes;
1558 }
1559 }
1560 if( wait_redraw ) {
1562 calendar::once_every( std::min( 1_minutes, wait_refresh_rate ) ) ) {
1563 if( first_redraw_since_waiting_started || calendar::once_every( wait_refresh_rate ) ) {
1565 }
1566
1567 // Avoid redrawing the main UI every time due to invalidation
1569 wait_popup = std::make_unique<static_popup>();
1570 wait_popup->on_top( true ).wait_message( "%s", wait_message );
1574 }
1575 } else {
1576 // Nothing to wait for now
1577 wait_popup.reset();
1579 }
1580
1583 u.apply_wetness_morale( weather.temperature );
1584
1585 if( !u.is_deaf() ) {
1587 }
1592
1593 // reset player noise
1594 u.volume = 0;
1595
1596 return false;
1597}
void action_taken()
Called after every action, invalidates player caches.
Definition: character.cpp:813
bool check_mount_is_spooked()
Definition: character.cpp:1042
void process_turn() override
Handles end-of-turn processing.
void update_bodytemp(const map &m, const weather_manager &weather)
Maintains body temperature.
Definition: character.cpp:5216
bool is_mounted() const
Definition: character.cpp:1083
bool has_destination() const
scenttype_id get_type_of_scent() const
Definition: character.cpp:8762
bool is_dead_state() const override
Returns true if the character should be dead.
Definition: character.cpp:500
bool is_deaf() const
Definition: character.cpp:4511
void update_body()
Updates all "biology" by one turn.
Definition: character.cpp:4690
bool has_active_bionic(const bionic_id &b) const
Returns true if the player has the entered bionic id and it is powered on.
Definition: character.cpp:1825
void apply_wetness_morale(int temperature)
Recalculates morale penalty/bonus from wetness based on mutations, equipment and temperature.
Definition: suffer.cpp:1874
virtual bool is_underwater() const
Definition: creature.cpp:172
static DynamicDataLoader & get_instance()
Returns the single instance of this class.
Definition: init.cpp:120
int get_levz() const
Definition: game.cpp:11937
void overmap_npc_move()
Definition: game.cpp:4205
class game::debug_hour_timer debug_hour_timer
npc_range all_npcs()
Same as all_creatures but iterators only over npcs.
Definition: game.cpp:12047
void monmove()
Definition: game.cpp:4079
void autopilot_vehicles()
process vehicles that are following the player
Definition: game.cpp:1662
void add_artifact_dreams()
Definition: game.cpp:11879
int moves_since_last_save
Definition: game.h:1039
bool take_screenshot() const
Saves a screenshot of the current viewport, as a PNG file.
Definition: game.cpp:7176
void calc_driving_offset(vehicle *veh=nullptr)
Definition: game.cpp:1248
bool cleanup_at_end()
Definition: game.cpp:944
std::unique_ptr< static_popup > wait_popup
Definition: game.h:1075
bool queue_screenshot
Definition: game.h:1018
friend weather_manager & get_weather()
Definition: weather.cpp:64
void autosave()
Definition: game.cpp:11368
void process_activity()
Definition: game.cpp:1651
void update_stair_monsters()
Definition: game.cpp:10842
void process_voluntary_act_interrupt()
Definition: game.cpp:1611
void load_npcs()
Makes any nearby NPCs on the overmap active.
Definition: game.cpp:818
bool npcs_dirty
Has a NPC been spawned since last load?
Definition: game.h:1046
void cleanup_dead()
Definition: game.cpp:4044
bool is_game_over()
Definition: game.cpp:2368
void perhaps_add_random_npc()
Definition: game.cpp:11100
void mon_info_update()
Definition: game.cpp:3843
bool handle_action()
const T & obj() const
Definition: ammo_effect.cpp:26
void build_floor_caches()
Definition: map.cpp:8196
void process_falling()
Invoked drop_everything on cached dirty tiles.
Definition: map.cpp:2356
void emit_field(const tripoint &pos, const emit_id &src, float mul=1.0f)
Runs one cycle of emission src which may result in propagation of fields.
Definition: map_field.cpp:1928
const std::vector< tripoint > & get_furn_field_locations() const
Definition: map.cpp:7888
void spawn_monsters(bool ignore_sight)
Spawn monsters from submap spawn points and from the overmap.
Definition: map.cpp:7847
void vehmove()
Definition: map.cpp:474
void creature_in_field(Creature &critter)
Apply field effects to the creature when it's on a square with fields.
Definition: map_field.cpp:1563
void process_fields()
Definition: map_field.cpp:142
furn_id furn(const tripoint &p) const
Definition: map.cpp:1413
void build_map_cache(int zlev, bool skip_lightmap=false)
Definition: map.cpp:8362
void process_items()
Definition: map.cpp:4700
static void process_all()
Handles mission deadline processing.
Definition: mission.cpp:98
void set_scent(const tripoint_abs_omt &loc, int strength)
Method to set a scent trace.
void process_mongroups()
Process nearby monstergroups (dying mostly).
void move_hordes()
Let hordes move a step.
const activity_id & id() const
std::optional< std::string > get_progress_message(const avatar &u) const
Helper that returns an activity specific progress message.
int volume
Definition: player.h:236
int scent
Definition: player.h:245
void set(const tripoint &p, int value, const scenttype_id &type=scenttype_id())
Get the scent value at the given position.
Definition: scent_map.cpp:102
void update(const tripoint &center, map &m)
Definition: scent_map.cpp:150
static constexpr time_duration from_minutes(const T m)
Definition: calendar.h:212
void process()
Process all queued events, potentially altering the game state and modifying the event queue.
static const activity_id ACT_AUTODRIVE("ACT_AUTODRIVE")
static const efftype_id effect_sleep("sleep")
@ QUIT_WATCH
Definition: game.h:73
static constexpr int MAX_VIEW_DISTANCE
void handle_weather_effects(const weather_type_id &w)
Definition: weather.cpp:522
bool once_every(const time_duration &event_frequency)
Predicate to handle rate-limiting.
Definition: calendar.cpp:490
void run_on_every_x_hooks(lua_state &)
Definition: catalua.cpp:92
void update_body_wetness(Character &who, const w_point &weather)
Maintains body wetness and handles the rate at which the player dries.
explosion_queue & get_explosion_queue()
Definition: explosion.cpp:1921
void do_vehicle_engine_sfx()
Definition: sounds.cpp:1613
void do_hearing_loss(int turns=-1)
Definition: sounds.cpp:1608
void do_danger_music()
Definition: sounds.cpp:1612
void do_vehicle_exterior_engine_sfx()
Definition: sounds.cpp:1614
void do_fatigue()
Definition: sounds.cpp:1633
void remove_hearing_loss()
Definition: sounds.cpp:1609
void process_sound_markers(player *p)
Definition: sounds.cpp:387
void process_sounds()
Definition: sounds.cpp:305
void reset_markers()
Definition: sounds.cpp:573
vehicle * veh_pointer_or_null(const optional_vpart_position &p)

References _, ACT_AUTODRIVE, Character::action_taken(), Character::activity, add_artifact_dreams(), all_npcs(), Character::apply_wetness_morale(), autopilot_vehicles(), autosave(), map::build_floor_caches(), map::build_map_cache(), calc_driving_offset(), Character::check_mount_is_spooked(), cleanup_at_end(), cleanup_dead(), Character::controlling_vehicle, map::creature_in_field(), sfx::do_danger_music(), sfx::do_fatigue(), sfx::do_hearing_loss(), sfx::do_vehicle_engine_sfx(), sfx::do_vehicle_exterior_engine_sfx(), driving_view_offset, effect_sleep, map::emit_field(), explosion_handler::explosion_queue::execute(), first_redraw_since_waiting_started, time_duration::from_minutes(), map::furn(), gamemode, explosion_handler::get_explosion_queue(), map::get_furn_field_locations(), DynamicDataLoader::get_instance(), get_levz(), player_activity::get_progress_message(), Character::get_type_of_scent(), get_weather, Character::global_omt_location(), grid_tracker_ptr, handle_action(), vehicle::handle_potential_theft(), handle_weather_effects(), Character::has_active_bionic(), Character::has_destination(), Character::has_distant_destination(), Creature::has_effect(), Character::has_trait(), player_activity::id(), Character::in_vehicle, invalidate_main_ui_adaptor(), Character::is_dead_state(), Character::is_deaf(), is_game_over(), Character::is_mounted(), Creature::is_underwater(), load_npcs(), m, MAX_VIEW_DISTANCE, mon_info_update(), monmove(), overmapbuffer::move_hordes(), Creature::moves, moves_since_last_save, new_game, npcs_dirty, int_id< T >::obj(), calendar::once_every(), overmap_buffer, overmap_npc_move(), perhaps_add_random_npc(), Character::pos(), game::debug_hour_timer::print_time(), timed_event_manager::process(), process_activity(), mission::process_all(), map::process_falling(), map::process_fields(), map::process_items(), overmapbuffer::process_mongroups(), sounds::process_sound_markers(), sounds::process_sounds(), Character::process_turn(), process_voluntary_act_interrupt(), queue_screenshot, QUIT_WATCH, ui_manager::redraw(), refresh_display(), sfx::remove_hearing_loss(), reset_light_level(), sounds::reset_markers(), rl_dist(), cata::run_on_every_x_hooks(), scent, player::scent, scent_map::set(), overmapbuffer::set_scent(), map::spawn_monsters(), take_screenshot(), timed_events, calendar::turn, u, scent_map::update(), Character::update_body(), character_funcs::update_body_wetness(), Character::update_bodytemp(), update_stair_monsters(), uquit, map::veh_at(), veh_pointer_or_null(), map::vehmove(), player::volume, wait_popup, point::x, and point::y.

◆ draw()

void game::draw ( )

Definition at line 3102 of file game.cpp.

3103{
3104 if( test_mode ) {
3105 return;
3106 }
3107
3108 //temporary fix for updating visibility for minimap
3109 ter_view_p.z = ( u.pos() + u.view_offset ).z;
3112
3113 werase( w_terrain );
3114 draw_ter();
3115 for( auto it = draw_callbacks.begin(); it != draw_callbacks.end(); ) {
3116 shared_ptr_fast<draw_callback_t> cb = it->lock();
3117 if( cb ) {
3118 ( *cb )();
3119 ++it;
3120 } else {
3121 it = draw_callbacks.erase( it );
3122 }
3123 }
3125
3126 draw_panels( true );
3127}
bool test_mode
Set to true when running in test mode (e.g.
tripoint ter_view_p
Definition: game.h:985
void draw_panels(bool force_draw=false)
Definition: game.cpp:3129
void draw_ter(bool draw_sounds=true)
Definition: game.cpp:3243
void update_visibility_cache(int zlev)
Definition: map.cpp:5736
int z
Definition: point.h:138

References map::build_map_cache(), draw_callbacks, draw_panels(), draw_ter(), m, Character::pos(), ter_view_p, test_mode, u, map::update_visibility_cache(), player::view_offset, w_terrain, catacurses::werase(), catacurses::wnoutrefresh(), and tripoint::z.

◆ draw_below_override()

void game::draw_below_override ( const tripoint p,
bool  draw 
)

Definition at line 1023 of file animation.cpp.

1024{
1025}

◆ draw_bullet()

void game::draw_bullet ( const tripoint t,
int  i,
const std::vector< tripoint > &  trajectory,
char  bullet 
)

Definition at line 578 of file animation.cpp.

580{
581 draw_bullet_curses( m, t, bullet, &trajectory[i] );
582}
void draw_bullet_curses(map &m, const tripoint &t, const char bullet, const tripoint *const p)
Definition: animation.cpp:460
std::vector< tripoint > trajectory
Definition: ranged.h:37

References anonymous_namespace{animation.cpp}::draw_bullet_curses(), and m.

◆ draw_critter()

void game::draw_critter ( const Creature critter,
const tripoint center 
)

Definition at line 3225 of file game.cpp.

3226{
3227 draw_critter_internal( w_terrain, critter, center, false, m, u );
3228}
static void draw_critter_internal(const catacurses::window &w, const Creature &critter, const tripoint &center, bool inverted, const map &m, const avatar &u)
Definition: game.cpp:3192

References center, draw_critter_internal(), m, u, and w_terrain.

Referenced by draw_ter().

◆ draw_critter_highlighted()

void game::draw_critter_highlighted ( const Creature critter,
const tripoint center 
)

Definition at line 3230 of file game.cpp.

3231{
3232 draw_critter_internal( w_terrain, critter, center, true, m, u );
3233}

References center, draw_critter_internal(), m, u, and w_terrain.

◆ draw_cursor()

void game::draw_cursor ( const tripoint p)

Definition at line 784 of file animation.cpp.

785{
786 const tripoint rp = relative_view_pos( *this, p );
787 mvwputch_inv( w_terrain, rp.xy(), c_light_green, 'X' );
788}
#define c_light_green
Definition: color.h:28
tripoint relative_view_pos(const game &g, const tripoint &p) noexcept
Definition: animation.cpp:128
void mvwputch_inv(const catacurses::window &w, point p, nc_color FG, int ch)
Definition: output.cpp:491

References c_light_green, mvwputch_inv(), anonymous_namespace{animation.cpp}::relative_view_pos(), w_terrain, and tripoint::xy().

Referenced by draw_look_around_cursor().

◆ draw_field_override()

void game::draw_field_override ( const tripoint p,
const field_type_id id 
)

Definition at line 979 of file animation.cpp.

980{
981}

◆ draw_furniture_override()

void game::draw_furniture_override ( const tripoint p,
const furn_id id 
)

Definition at line 940 of file animation.cpp.

941{
942}

◆ draw_graffiti_override()

void game::draw_graffiti_override ( const tripoint p,
bool  has 
)

Definition at line 953 of file animation.cpp.

954{
955}

◆ draw_highlight()

void game::draw_highlight ( const tripoint p)

Definition at line 797 of file animation.cpp.

798{
799 // Do nothing
800}

◆ draw_hit_mon()

void game::draw_hit_mon ( const tripoint p,
const monster m,
bool  dead = false 
)

Definition at line 641 of file animation.cpp.

642{
643 draw_hit_mon_curses( p, m, u, dead );
644}
void draw_hit_mon_curses(const tripoint &center, const monster &m, const player &u, const bool dead)
Definition: animation.cpp:612

References dead, anonymous_namespace{animation.cpp}::draw_hit_mon_curses(), m, and u.

◆ draw_hit_player()

void game::draw_hit_player ( const Character p,
int  dam 
)

Definition at line 686 of file animation.cpp.

687{
688 draw_hit_player_curses( *this, p, dam );
689}
void draw_hit_player_curses(const game &g, const Character &p, const int dam)
Definition: animation.cpp:649

References anonymous_namespace{animation.cpp}::draw_hit_player_curses().

◆ draw_item_override()

void game::draw_item_override ( const tripoint p,
const itype_id id,
const mtype_id mid,
bool  hilite 
)

Definition at line 993 of file animation.cpp.

995{
996}

◆ draw_line() [1/2]

void game::draw_line ( const tripoint p,
const std::vector< tripoint > &  points 
)

Definition at line 770 of file animation.cpp.

771{
772 draw_line_curses( *this, points );
773}
void draw_line_curses(game &g, const std::vector< tripoint > &points)
Definition: animation.cpp:750

References anonymous_namespace{animation.cpp}::draw_line_curses().

◆ draw_line() [2/2]

void game::draw_line ( const tripoint p,
const tripoint center_point,
const std::vector< tripoint > &  points,
bool  noreveal = false 
)

Definition at line 737 of file animation.cpp.

739{
740 if( !u.sees( p ) ) {
741 return;
742 }
743
744 draw_line_curses( *this, center, points, noreveal );
745}

References center, anonymous_namespace{animation.cpp}::draw_line_curses(), Character::sees(), and u.

Referenced by draw_ter().

◆ draw_look_around_cursor()

void game::draw_look_around_cursor ( const tripoint lp,
const visibility_variables cache 
)

Definition at line 5708 of file game.cpp.

5709{
5710 if( !liveview.is_enabled() ) {
5711#if defined( TILES )
5712 if( is_draw_tiles_mode() ) {
5713 draw_cursor( lp );
5714 return;
5715 }
5716#endif
5717 const tripoint view_center = u.pos() + u.view_offset;
5718 visibility_type visibility = VIS_HIDDEN;
5719 const bool inbounds = m.inbounds( lp );
5720 if( inbounds ) {
5721 visibility = m.get_visibility( m.apparent_light_at( lp, cache ), cache );
5722 }
5723 if( visibility == VIS_CLEAR ) {
5724 const Creature *const creature = critter_at( lp, true );
5725 if( creature != nullptr && u.sees( *creature ) ) {
5726 creature->draw( w_terrain, view_center, true );
5727 } else {
5728 m.drawsq( w_terrain, lp, drawsq_params().highlight( true ).center( view_center ) );
5729 }
5730 } else {
5731 std::string visibility_indicator;
5732 nc_color visibility_indicator_color = c_white;
5733 switch( visibility ) {
5734 case VIS_CLEAR:
5735 // Already handled by the outer if statement
5736 break;
5737 case VIS_BOOMER:
5738 case VIS_BOOMER_DARK:
5739 visibility_indicator = '#';
5740 visibility_indicator_color = c_pink;
5741 break;
5742 case VIS_DARK:
5743 visibility_indicator = '#';
5744 visibility_indicator_color = c_dark_gray;
5745 break;
5746 case VIS_LIT:
5747 visibility_indicator = '#';
5748 visibility_indicator_color = c_light_gray;
5749 break;
5750 case VIS_HIDDEN:
5751 visibility_indicator = 'x';
5752 visibility_indicator_color = c_white;
5753 break;
5754 }
5755
5756 const tripoint screen_pos = point( POSX, POSY ) + lp - view_center;
5757 mvwputch( w_terrain, screen_pos.xy(), visibility_indicator_color, visibility_indicator );
5758 }
5759 }
5760}
void draw_cursor(const tripoint &p)
Definition: animation.cpp:784
T * critter_at(const tripoint &p, bool allow_hallucination=false)
Returns the Creature at the given location.
Definition: game.cpp:4545
bool is_enabled()
Definition: live_view.cpp:75
virtual bool inbounds(const tripoint &p) const
Definition: map.cpp:7903
visibility_type get_visibility(lit_level ll, const visibility_variables &cache) const
Definition: map.cpp:5790
lit_level apparent_light_at(const tripoint &p, const visibility_variables &cache) const
Determine the visible light level for a tile, based on light_at for the tile, vision distance,...
Definition: lightmap.cpp:765
void drawsq(const catacurses::window &w, const tripoint &p, const drawsq_params &params) const
Draw the map tile at the given coordinate.
Definition: map.cpp:5968
#define c_dark_gray
Definition: color.h:20
#define c_pink
Definition: color.h:31
visibility_type
Definition: enums.h:57
@ VIS_CLEAR
Definition: enums.h:59
@ VIS_BOOMER
Definition: enums.h:61
@ VIS_DARK
Definition: enums.h:62
@ VIS_BOOMER_DARK
Definition: enums.h:63
@ VIS_HIDDEN
Definition: enums.h:58
@ VIS_LIT
Definition: enums.h:60
bool is_draw_tiles_mode()
Check whether we're in tile drawing mode.
Definition: output.cpp:2075
Draw parameters used by map::drawsq() and similar methods.
Definition: map.h:180

References map::apparent_light_at(), c_dark_gray, c_light_gray, c_pink, c_white, center, creature, critter_at(), draw_cursor(), map::drawsq(), map::get_visibility(), map::inbounds(), is_draw_tiles_mode(), live_view::is_enabled(), liveview, m, mvwputch(), Character::pos(), POSX, POSY, Character::sees(), u, player::view_offset, VIS_BOOMER, VIS_BOOMER_DARK, VIS_CLEAR, VIS_DARK, VIS_HIDDEN, VIS_LIT, w_terrain, and tripoint::xy().

Referenced by look_around().

◆ draw_minimap()

void game::draw_minimap ( )
private

Definition at line 3303 of file game.cpp.

3304{
3305
3306 // Draw the box
3307 werase( w_minimap );
3309
3310 const tripoint_abs_omt curs = u.global_omt_location();
3311 const point_abs_omt curs2( curs.xy() );
3313 bool drew_mission = targ == overmap::invalid_tripoint;
3314
3315 for( int i = -2; i <= 2; i++ ) {
3316 for( int j = -2; j <= 2; j++ ) {
3317 const point_abs_omt om( curs2 + point( i, j ) );
3318 nc_color ter_color;
3319 tripoint_abs_omt omp( om, get_levz() );
3320 std::string ter_sym;
3321 const bool seen = overmap_buffer.seen( omp );
3322 const bool vehicle_here = overmap_buffer.has_vehicle( omp );
3323 if( overmap_buffer.has_note( omp ) ) {
3324
3325 const std::string &note_text = overmap_buffer.note( omp );
3326
3327 ter_color = c_yellow;
3328 ter_sym = "N";
3329
3330 int symbolIndex = note_text.find( ':' );
3331 int colorIndex = note_text.find( ';' );
3332
3333 bool symbolFirst = symbolIndex < colorIndex;
3334
3335 if( colorIndex > -1 && symbolIndex > -1 ) {
3336 if( symbolFirst ) {
3337 if( colorIndex > 4 ) {
3338 colorIndex = -1;
3339 }
3340 if( symbolIndex > 1 ) {
3341 symbolIndex = -1;
3342 colorIndex = -1;
3343 }
3344 } else {
3345 if( symbolIndex > 4 ) {
3346 symbolIndex = -1;
3347 }
3348 if( colorIndex > 2 ) {
3349 colorIndex = -1;
3350 }
3351 }
3352 } else if( colorIndex > 2 ) {
3353 colorIndex = -1;
3354 } else if( symbolIndex > 1 ) {
3355 symbolIndex = -1;
3356 }
3357
3358 if( symbolIndex > -1 ) {
3359 int symbolStart = 0;
3360 if( colorIndex > -1 && !symbolFirst ) {
3361 symbolStart = colorIndex + 1;
3362 }
3363 ter_sym = note_text.substr( symbolStart, symbolIndex - symbolStart ).c_str()[0];
3364 }
3365
3366 if( colorIndex > -1 ) {
3367
3368 int colorStart = 0;
3369
3370 if( symbolIndex > -1 && symbolFirst ) {
3371 colorStart = symbolIndex + 1;
3372 }
3373
3374 std::string sym = note_text.substr( colorStart, colorIndex - colorStart );
3375
3376 if( sym.length() == 2 ) {
3377 if( sym == "br" ) {
3378 ter_color = c_brown;
3379 } else if( sym == "lg" ) {
3380 ter_color = c_light_gray;
3381 } else if( sym == "dg" ) {
3382 ter_color = c_dark_gray;
3383 }
3384 } else {
3385 char colorID = sym.c_str()[0];
3386 if( colorID == 'r' ) {
3387 ter_color = c_light_red;
3388 } else if( colorID == 'R' ) {
3389 ter_color = c_red;
3390 } else if( colorID == 'g' ) {
3391 ter_color = c_light_green;
3392 } else if( colorID == 'G' ) {
3393 ter_color = c_green;
3394 } else if( colorID == 'b' ) {
3395 ter_color = c_light_blue;
3396 } else if( colorID == 'B' ) {
3397 ter_color = c_blue;
3398 } else if( colorID == 'W' ) {
3399 ter_color = c_white;
3400 } else if( colorID == 'C' ) {
3401 ter_color = c_cyan;
3402 } else if( colorID == 'c' ) {
3403 ter_color = c_light_cyan;
3404 } else if( colorID == 'P' ) {
3405 ter_color = c_pink;
3406 } else if( colorID == 'm' ) {
3407 ter_color = c_magenta;
3408 }
3409 }
3410 }
3411 } else if( !seen ) {
3412 ter_sym = " ";
3413 ter_color = c_black;
3414 } else if( vehicle_here ) {
3415 ter_color = c_cyan;
3416 ter_sym = "c";
3417 } else {
3418 const oter_id &cur_ter = overmap_buffer.ter( omp );
3419 ter_sym = cur_ter->get_symbol();
3420 if( overmap_buffer.is_explored( omp ) ) {
3421 ter_color = c_dark_gray;
3422 } else {
3423 ter_color = cur_ter->get_color();
3424 }
3425 }
3426 if( !drew_mission && targ.xy() == omp.xy() ) {
3427 // If there is a mission target, and it's not on the same
3428 // overmap terrain as the player character, mark it.
3429 // TODO: Inform player if the mission is above or below
3430 drew_mission = true;
3431 if( i != 0 || j != 0 ) {
3432 ter_color = red_background( ter_color );
3433 }
3434 }
3435 if( i == 0 && j == 0 ) {
3436 mvwputch_hi( w_minimap, point( 3, 3 ), ter_color, ter_sym );
3437 } else {
3438 mvwputch( w_minimap, point( 3 + i, 3 + j ), ter_color, ter_sym );
3439 }
3440 }
3441 }
3442
3443 // Print arrow to mission if we have one!
3444 if( !drew_mission ) {
3445 double slope = curs2.x() != targ.x() ?
3446 static_cast<double>( targ.y() - curs2.y() ) / ( targ.x() - curs2.x() ) : 4;
3447
3448 if( curs2.x() == targ.x() || std::fabs( slope ) > 3.5 ) { // Vertical slope
3449 if( targ.y() > curs2.y() ) {
3450 mvwputch( w_minimap, point( 3, 6 ), c_red, "*" );
3451 } else {
3452 mvwputch( w_minimap, point( 3, 0 ), c_red, "*" );
3453 }
3454 } else {
3455 int arrowx = -1;
3456 int arrowy = -1;
3457 if( std::fabs( slope ) >= 1. ) { // y diff is bigger!
3458 arrowy = targ.y() > curs2.y() ? 6 : 0;
3459 arrowx =
3460 static_cast<int>( 3 + 3 * ( targ.y() > curs2.y() ? slope : ( 0 - slope ) ) );
3461 if( arrowx < 0 ) {
3462 arrowx = 0;
3463 }
3464 if( arrowx > 6 ) {
3465 arrowx = 6;
3466 }
3467 } else {
3468 arrowx = targ.x() > curs2.x() ? 6 : 0;
3469 arrowy = static_cast<int>( 3 + 3 * ( targ.x() > curs2.x() ? slope : -slope ) );
3470 if( arrowy < 0 ) {
3471 arrowy = 0;
3472 }
3473 if( arrowy > 6 ) {
3474 arrowy = 6;
3475 }
3476 }
3477 char glyph = '*';
3478 if( targ.z() > u.posz() ) {
3479 glyph = '^';
3480 } else if( targ.z() < u.posz() ) {
3481 glyph = 'v';
3482 }
3483
3484 mvwputch( w_minimap, point( arrowx, arrowy ), c_red, glyph );
3485 }
3486 }
3487
3488 const int sight_points = g->u.overmap_sight_range( g->light_level( g->u.posz() ) );
3489 for( int i = -3; i <= 3; i++ ) {
3490 for( int j = -3; j <= 3; j++ ) {
3491 if( i > -3 && i < 3 && j > -3 && j < 3 ) {
3492 continue; // only do hordes on the border, skip inner map
3493 }
3494 const tripoint_abs_omt omp( curs2 + point( i, j ), get_levz() );
3496 if( overmap_buffer.seen( omp )
3497 && g->u.overmap_los( omp, sight_points ) ) {
3498 mvwputch( w_minimap, point( i + 3, j + 3 ), c_green,
3499 overmap_buffer.get_horde_size( omp ) > HORDE_VISIBILITY_SIZE * 2 ? 'Z' : 'z' );
3500 }
3501 }
3502 }
3503 }
3504
3506}
tripoint_abs_omt get_active_mission_target() const
Returns the target of the active mission or overmap::invalid_tripoint if there is no active mission.
Definition: avatar.cpp:207
constexpr auto & x()
Definition: coordinates.h:118
constexpr auto & z()
Definition: coordinates.h:133
constexpr auto & y()
Definition: coordinates.h:124
constexpr auto xy() const
Definition: coordinates.h:130
static constexpr tripoint_abs_omt invalid_tripoint
Dummy value, used to indicate that a point returned by a function is invalid.
Definition: overmap.h:260
bool seen(const tripoint_abs_omt &p)
const std::string & note(const tripoint_abs_omt &p)
int get_horde_size(const tripoint_abs_omt &p)
bool is_explored(const tripoint_abs_omt &p)
const oter_id & ter(const tripoint_abs_omt &p)
Returns the overmap terrain at the given OMT coordinates.
bool has_note(const tripoint_abs_omt &p)
Uses global overmap terrain coordinates.
bool has_vehicle(const tripoint_abs_omt &p)
nc_color red_background(const nc_color &c)
Definition: color.cpp:515
#define c_blue
Definition: color.h:23
#define c_black
Definition: color.h:17
#define c_light_blue
Definition: color.h:29
#define c_yellow
Definition: color.h:32
#define c_light_cyan
Definition: color.h:30
#define c_cyan
Definition: color.h:24
#define c_light_red
Definition: color.h:27
static constexpr int HORDE_VISIBILITY_SIZE
constexpr scale om
Definition: coordinates.h:34
void mvwputch_hi(const catacurses::window &w, point p, nc_color FG, int ch)
Definition: output.cpp:508
std::string get_symbol(const bool from_land_use_code=false) const
Definition: omdata.h:209
nc_color get_color(const bool from_land_use_code=false) const
Definition: omdata.h:217

References c_black, c_blue, c_brown, c_cyan, c_dark_gray, c_green, c_light_blue, c_light_cyan, c_light_gray, c_light_green, c_light_red, c_magenta, c_pink, c_red, c_white, c_yellow, draw_border(), units::fabs(), g, avatar::get_active_mission_target(), oter_t::get_color(), overmapbuffer::get_horde_size(), get_levz(), oter_t::get_symbol(), Character::global_omt_location(), overmapbuffer::has_note(), overmapbuffer::has_vehicle(), HORDE_VISIBILITY_SIZE, overmap::invalid_tripoint, overmapbuffer::is_explored(), mvwputch(), mvwputch_hi(), overmapbuffer::note(), coords::om, overmap_buffer, Character::posz(), red_background(), overmapbuffer::seen(), overmapbuffer::ter(), u, w_minimap, catacurses::werase(), catacurses::wnoutrefresh(), coords::coord_point< Point, Origin, Scale >::x(), coords::coord_point< Point, Origin, Scale >::xy(), coords::coord_point< Point, Origin, Scale >::y(), and coords::coord_point< Point, Origin, Scale >::z().

◆ draw_monster_override()

void game::draw_monster_override ( const tripoint p,
const mtype_id id,
int  count,
bool  more,
Creature::Attitude  att 
)

Definition at line 1037 of file animation.cpp.

1039{
1040}

◆ draw_panels()

void game::draw_panels ( bool  force_draw = false)

Definition at line 3129 of file game.cpp.

3130{
3131 static int previous_turn = -1;
3132 const int current_turn = to_turns<int>( calendar::turn - calendar::turn_zero );
3133 const bool draw_this_turn = current_turn > previous_turn || force_draw;
3134 auto &mgr = panel_manager::get_manager();
3135 int y = 0;
3136 const bool sidebar_right = get_option<std::string>( "SIDEBAR_POSITION" ) == "right";
3137 int spacer = get_option<bool>( "SIDEBAR_SPACERS" ) ? 1 : 0;
3138 int log_height = 0;
3139 for( const window_panel &panel : mgr.get_current_layout() ) {
3140 if( panel.get_height() != -2 && panel.toggle && panel.render() ) {
3141 log_height += panel.get_height() + spacer;
3142 }
3143 }
3144 log_height = std::max( TERMY - log_height, 3 );
3145 for( const window_panel &panel : mgr.get_current_layout() ) {
3146 if( panel.render() ) {
3147 // height clamped to window height.
3148 int h = std::min( panel.get_height(), TERMY - y );
3149 if( h == -2 ) {
3150 h = log_height;
3151 }
3152 h += spacer;
3153 if( panel.toggle && panel.render() && h > 0 ) {
3154 if( panel.always_draw || draw_this_turn ) {
3155 panel.draw( u, catacurses::newwin( h, panel.get_width(),
3156 point( sidebar_right ? TERMX - panel.get_width() : 0, y ) ) );
3157 }
3158 if( show_panel_adm ) {
3159 const std::string panel_name = _( panel.get_name() );
3160 const int panel_name_width = utf8_width( panel_name );
3161 auto label = catacurses::newwin( 1, panel_name_width, point( sidebar_right ?
3162 TERMX - panel.get_width() - panel_name_width - 1 : panel.get_width() + 1, y ) );
3163 werase( label );
3164 mvwprintz( label, point_zero, c_light_red, panel_name );
3166 label = catacurses::newwin( h, 1,
3167 point( sidebar_right ? TERMX - panel.get_width() - 1 : panel.get_width(), y ) );
3168 werase( label );
3169 if( h == 1 ) {
3171 } else {
3173 for( int i = 1; i < h - 1; i++ ) {
3175 }
3176 mvwputch( label, point( 0, h - 1 ), c_light_red, sidebar_right ? LINE_XXOO : LINE_XOOX );
3177 }
3179 }
3180 y += h;
3181 }
3182 }
3183 }
3184 previous_turn = current_turn;
3185}
bool show_panel_adm
Definition: game.h:1013
const time_point turn_zero
Represents time point 0.
Definition: calendar.cpp:26
#define LINE_XOXO
Definition: output.h:39
#define LINE_OXOX
Definition: output.h:40
#define LINE_OXXX
Definition: output.h:48
#define LINE_XOOX
Definition: output.h:44
#define LINE_XXOO
Definition: output.h:41
Struct used for storing labels (easier to json opposed to a std::map<point, std::string>)
Definition: vehicle.h:286

References _, c_light_red, panel_manager::get_manager(), LINE_OXOX, LINE_OXXX, LINE_XOOX, LINE_XOXO, LINE_XXOO, mvwprintz(), mvwputch(), catacurses::newwin(), point_zero, show_panel_adm, TERMX, TERMY, calendar::turn, calendar::turn_zero, u, utf8_width(), catacurses::werase(), and catacurses::wnoutrefresh().

Referenced by draw().

◆ draw_pixel_minimap()

void game::draw_pixel_minimap ( const catacurses::window w)

Definition at line 3187 of file game.cpp.

3188{
3189 w_pixel_minimap = w;
3190}

References w_pixel_minimap.

◆ draw_radiation_override()

void game::draw_radiation_override ( const tripoint p,
int  rad 
)

Definition at line 914 of file animation.cpp.

915{
916}

◆ draw_sct()

void game::draw_sct ( )

Definition at line 865 of file animation.cpp.

866{
867 draw_sct_curses( *this );
868}
void draw_sct_curses(const game &g)
Definition: animation.cpp:832

References anonymous_namespace{animation.cpp}::draw_sct_curses().

Referenced by get_player_input().

◆ draw_ter() [1/2]

void game::draw_ter ( bool  draw_sounds = true)

Definition at line 3243 of file game.cpp.

3244{
3246 draw_sounds );
3247}
bool is_looking
Definition: game.h:224

References draw_ter(), is_looking, Character::pos(), u, and player::view_offset.

Referenced by draw(), and draw_ter().

◆ draw_ter() [2/2]

void game::draw_ter ( const tripoint center,
bool  looking = false,
bool  draw_sounds = true 
)

Definition at line 3249 of file game.cpp.

3250{
3252
3253 m.draw( w_terrain, center );
3254
3255 if( draw_sounds ) {
3257 }
3258
3259 for( Creature &critter : all_creatures() ) {
3260 draw_critter( critter, center );
3261 }
3262
3263 if( !destination_preview.empty() && u.view_offset.z == 0 ) {
3264 // Draw auto-move preview trail
3265 const tripoint &final_destination = destination_preview.back();
3266 tripoint line_center = u.pos() + u.view_offset;
3267 draw_line( final_destination, line_center, destination_preview, true );
3268 mvwputch( w_terrain, final_destination.xy() - u.view_offset.xy() + point( POSX - u.posx(),
3269 POSY - u.posy() ), c_white, 'X' );
3270 }
3271
3272 if( u.controlling_vehicle && !looking ) {
3273 draw_veh_dir_indicator( false );
3274 draw_veh_dir_indicator( true );
3275 }
3276 // Place the cursor over the player as is expected by screen readers.
3277 wmove( w_terrain, -center.xy() + g->u.pos().xy() + point( POSX, POSY ) );
3278}
int posx() const override
Definition: character.h:797
int posy() const override
Definition: character.h:800
void draw_critter(const Creature &critter, const tripoint &center)
Definition: game.cpp:3225
Creature_range all_creatures()
Returns an anonymous range that contains all creatures.
Definition: game.cpp:12037
std::vector< tripoint > destination_preview
Definition: game.h:1065
void draw_veh_dir_indicator(bool next)
Definition: game.cpp:3295
void draw_line(const tripoint &p, const tripoint &center_point, const std::vector< tripoint > &points, bool noreveal=false)
Definition: animation.cpp:737
void draw(const catacurses::window &w, const tripoint &center)
Draw a visible part of the map into w.
Definition: map.cpp:5840
static void draw_footsteps(const catacurses::window &window, const tripoint &offset)
Definition: game.cpp:2915
void wmove(const window &win, point p)
Definition: ncurses_def.cpp:98

References all_creatures(), c_white, center, Character::controlling_vehicle, destination_preview, map::draw(), draw_critter(), draw_footsteps(), draw_line(), draw_veh_dir_indicator(), g, m, mvwputch(), Character::pos(), Character::posx(), POSX, Character::posy(), POSY, ter_view_p, u, player::view_offset, w_terrain, catacurses::wmove(), tripoint::xy(), and tripoint::z.

◆ draw_terrain_override()

void game::draw_terrain_override ( const tripoint p,
const ter_id id 
)

Definition at line 927 of file animation.cpp.

928{
929}

◆ draw_trail_to_square()

void game::draw_trail_to_square ( const tripoint t,
bool  bDrawX 
)

Definition at line 7024 of file game.cpp.

7025{
7026 ::draw_trail( u.pos(), u.pos() + t, bDrawX );
7027}
static void draw_trail(const tripoint &start, const tripoint &end, bool bDrawX)
Definition: game.cpp:6994

References draw_trail(), Character::pos(), and u.

◆ draw_trap_override()

void game::draw_trap_override ( const tripoint p,
const trap_id id 
)

Definition at line 966 of file animation.cpp.

967{
968}

◆ draw_veh_dir_indicator()

void game::draw_veh_dir_indicator ( bool  next)

Definition at line 3295 of file game.cpp.

3296{
3297 if( const std::optional<tripoint> indicator_offset = get_veh_dir_indicator_location( next ) ) {
3298 auto col = next ? c_white : c_dark_gray;
3299 mvwputch( w_terrain, indicator_offset->xy() - u.view_offset.xy() + point( POSX, POSY ), col, 'X' );
3300 }
3301}
std::optional< tripoint > get_veh_dir_indicator_location(bool next) const
Returns the location where the indicator should go relative to the reality bubble,...
Definition: game.cpp:3280

References c_dark_gray, c_white, get_veh_dir_indicator_location(), mvwputch(), POSX, POSY, u, player::view_offset, w_terrain, and tripoint::xy().

Referenced by draw_ter().

◆ draw_vpart_override()

void game::draw_vpart_override ( const tripoint p,
const vpart_id id,
int  part_mod,
units::angle  veh_dir,
bool  hilite,
point  mount 
)

Definition at line 1009 of file animation.cpp.

1011{
1012}

◆ draw_weather()

void game::draw_weather ( const weather_printable wPrint)

Definition at line 824 of file animation.cpp.

825{
827}
void draw_weather_curses(const catacurses::window &win, const weather_printable &w)
Definition: animation.cpp:805

References anonymous_namespace{animation.cpp}::draw_weather_curses(), and w_terrain.

Referenced by get_player_input().

◆ draw_zones()

void game::draw_zones ( const tripoint start,
const tripoint end,
const tripoint offset 
)

Definition at line 900 of file animation.cpp.

901{
902 draw_zones_curses( w_terrain, start, end, offset );
903}
void draw_zones_curses(const catacurses::window &w, const tripoint &start, const tripoint &end, const tripoint &offset)
Definition: animation.cpp:873

References anonymous_namespace{animation.cpp}::draw_zones_curses(), and w_terrain.

◆ drop()

void game::drop ( )
private

Definition at line 8072 of file game.cpp.

8073{
8075}
void drop(item_location loc, const tripoint &where)
Drops an item to the specified location.
Definition: character.cpp:2453
drop_locations multidrop(player &p)
Select items to drop.

References Character::drop(), game_menus::inv::multidrop(), Character::pos(), and u.

Referenced by handle_action().

◆ drop_in_direction()

void game::drop_in_direction ( )
private

Definition at line 8077 of file game.cpp.

8078{
8079 if( const std::optional<tripoint> pnt = choose_adjacent( _( "Drop where?" ) ) ) {
8080 u.drop( game_menus::inv::multidrop( u ), *pnt );
8081 }
8082}

References _, choose_adjacent(), Character::drop(), game_menus::inv::multidrop(), and u.

Referenced by handle_action().

◆ dump_stats()

bool game::dump_stats ( const std::string &  what,
dump_mode  mode,
const std::vector< std::string > &  opts 
)

write statistics to stdout and

Returns
true if successful

Definition at line 40 of file dump.cpp.

42{
43 try {
45 } catch( const std::exception &err ) {
46 std::cerr << "Error loading data from json: " << err.what() << std::endl;
47 return false;
48 }
49
50 std::vector<std::string> header;
51 std::vector<std::vector<std::string>> rows;
52
53 int scol = 0; // sorting column
54
55 std::map<std::string, standard_npc> test_npcs;
56 test_npcs[ "S1" ] = standard_npc( "S1", { 0, 0, 2 }, { "gloves_survivor", "mask_lsurvivor" },
57 4, 8, 10, 8, 10 /* DEX 10, PER 10 */ );
58 test_npcs[ "S2" ] = standard_npc( "S2", { 0, 0, 3 }, { "gloves_fingerless", "sunglasses" },
59 4, 8, 8, 8, 10 /* PER 10 */ );
60 test_npcs[ "S3" ] = standard_npc( "S3", { 0, 0, 4 }, { "gloves_plate", "helmet_plate" },
61 4, 10, 8, 8, 8 /* STAT 10 */ );
62 test_npcs[ "S4" ] = standard_npc( "S4", { 0, 0, 5 }, {}, 0, 8, 10, 8, 10 /* DEX 10, PER 10 */ );
63 test_npcs[ "S5" ] = standard_npc( "S5", { 0, 0, 6 }, {}, 4, 8, 10, 8, 10 /* DEX 10, PER 10 */ );
64 test_npcs[ "S6" ] = standard_npc( "S6", { 0, 0, 7 }, { "gloves_hsurvivor", "mask_hsurvivor" },
65 4, 8, 10, 8, 10 /* DEX 10, PER 10 */ );
66
67 std::map<std::string, item> test_items;
68 test_items[ "G1" ] = item( "glock_19" ).ammo_set( itype_id( "9mm" ) );
69 test_items[ "G2" ] = item( "hk_mp5" ).ammo_set( itype_id( "9mm" ) );
70 test_items[ "G3" ] = item( "ar15" ).ammo_set( itype_id( "223" ) );
71 test_items[ "G4" ] = item( "remington_700" ).ammo_set( itype_id( "270" ) );
72 test_items[ "G4" ].put_in( item( "rifle_scope" ) );
73
74 if( what == "AMMO" ) {
75 header = {
76 "Name", "Ammo", "Volume", "Weight", "Stack",
77 "Range", "Dispersion", "Recoil", "Damage", "Pierce", "Damage multiplier"
78 };
79 auto dump = [&rows]( const item & obj ) {
80 std::vector<std::string> r;
81 r.push_back( obj.tname( 1, false ) );
82 r.push_back( obj.ammo_type().str() );
83 r.push_back( std::to_string( obj.volume() / units::legacy_volume_factor ) );
84 r.push_back( std::to_string( to_gram( obj.weight() ) ) );
85 r.push_back( std::to_string( obj.type->stack_size ) );
86 r.push_back( std::to_string( obj.type->ammo->range ) );
87 r.push_back( std::to_string( obj.type->ammo->dispersion ) );
88 r.push_back( std::to_string( obj.type->ammo->recoil ) );
89 damage_instance damage = obj.type->ammo->damage;
90 r.push_back( std::to_string( damage.total_damage() ) );
91 r.push_back( std::to_string( damage.empty() ? 0 : ( *damage.begin() ).res_pen ) );
92 rows.push_back( r );
93 };
94 for( const itype *e : item_controller->all() ) {
95 if( e->ammo ) {
96 dump( item( e, calendar::turn, item::solitary_tag {} ) );
97 }
98 }
99
100 } else if( what == "ARMOR" ) {
101 header = {
102 "Name", "Encumber (fit)", "Warmth", "Weight", "Storage", "Coverage", "Bash", "Cut", "Bullet", "Acid", "Fire"
103 };
104 auto dump = [&rows]( const item & obj ) {
105 std::vector<std::string> r;
106 r.push_back( obj.tname( 1, false ) );
107 r.push_back( std::to_string( obj.get_encumber( g->u ) ) );
108 r.push_back( std::to_string( obj.get_warmth() ) );
109 r.push_back( std::to_string( to_gram( obj.weight() ) ) );
110 r.push_back( std::to_string( obj.get_storage() / units::legacy_volume_factor ) );
111 r.push_back( std::to_string( obj.get_coverage() ) );
112 r.push_back( std::to_string( obj.bash_resist() ) );
113 r.push_back( std::to_string( obj.cut_resist() ) );
114 r.push_back( std::to_string( obj.bullet_resist() ) );
115 r.push_back( std::to_string( obj.acid_resist() ) );
116 r.push_back( std::to_string( obj.fire_resist() ) );
117 rows.push_back( r );
118 };
119
120 body_part bp = opts.empty() ? num_bp : get_body_part_token( opts.front() );
121
122 for( const itype *e : item_controller->all() ) {
123 if( e->armor ) {
124 item obj( e );
125 if( bp == num_bp || obj.covers( bp ) ) {
126 if( obj.has_flag( flag_VARSIZE ) ) {
127 obj.set_flag( "FIT" );
128 }
129 dump( obj );
130 }
131 }
132 }
133
134 } else if( what == "EDIBLE" ) {
135 header = {
136 "Name", "Volume", "Weight", "Stack", "Calories", "Quench", "Healthy"
137 };
138 for( const auto &v : vitamin::all() ) {
139 header.push_back( v.second.name() );
140 }
141 auto dump = [&rows]( const item & obj ) {
142 std::vector<std::string> r;
143 r.push_back( obj.tname( 1, false ) );
144 r.push_back( std::to_string( obj.volume() / units::legacy_volume_factor ) );
145 r.push_back( std::to_string( to_gram( obj.weight() ) ) );
146 r.push_back( std::to_string( obj.type->stack_size ) );
147 r.push_back( std::to_string( obj.get_comestible()->default_nutrition.kcal ) );
148 r.push_back( std::to_string( obj.get_comestible()->quench ) );
149 r.push_back( std::to_string( obj.get_comestible()->healthy ) );
150 auto vits = obj.get_comestible()->default_nutrition.vitamins;
151 for( const auto &v : vitamin::all() ) {
152 r.push_back( std::to_string( vits[ v.first ] ) );
153 }
154 rows.push_back( r );
155 };
156
157 for( const itype *e : item_controller->all() ) {
159
160 if( food.is_food() && g->u.can_eat( food ).success() ) {
161 dump( food );
162 }
163 }
164
165 } else if( what == "GUN" ) {
166 header = {
167 "Name", "Ammo", "Volume", "Weight", "Capacity",
168 "Range", "Dispersion", "Effective recoil", "Damage", "Pierce",
169 "Aim time", "Effective range", "Snapshot range", "Max range"
170 };
171
172 std::set<std::string> locations;
173 for( const itype *e : item_controller->all() ) {
174 if( e->gun ) {
175 std::transform( e->gun->valid_mod_locations.begin(),
176 e->gun->valid_mod_locations.end(),
177 std::inserter( locations, locations.begin() ),
178 []( const std::pair<gunmod_location, int> &q ) {
179 return q.first.name();
180 } );
181 }
182 }
183 for( const auto &e : locations ) {
184 header.push_back( e );
185 }
186
187 auto dump = [&rows, &locations]( const standard_npc & who, const item & obj ) {
188 std::vector<std::string> r;
189 r.push_back( obj.tname( 1, false ) );
190 r.push_back( !obj.ammo_types().empty() ? enumerate_as_string( obj.ammo_types().begin(),
191 obj.ammo_types().end(), []( const ammotype & at ) {
192 return at.str();
194 r.push_back( std::to_string( obj.volume() / units::legacy_volume_factor ) );
195 r.push_back( std::to_string( to_gram( obj.weight() ) ) );
196 r.push_back( std::to_string( obj.ammo_capacity() ) );
197 r.push_back( std::to_string( obj.gun_range() ) );
198 r.push_back( std::to_string( obj.gun_dispersion() ) );
199 r.push_back( std::to_string( obj.gun_recoil() ) );
200 damage_instance damage = obj.gun_damage();
201 r.push_back( std::to_string( damage.total_damage() ) );
202 r.push_back( std::to_string( damage.empty() ? 0 : ( *damage.begin() ).res_pen ) );
203
204 r.push_back( std::to_string( ranged::gun_engagement_moves( who, obj ) ) );
205
206 for( const auto &e : locations ) {
207 const auto &vml = obj.type->gun->valid_mod_locations;
208 const auto iter = vml.find( e );
209 r.push_back( std::to_string( iter != vml.end() ? iter->second : 0 ) );
210 }
211 rows.push_back( r );
212 };
213 for( const itype *e : item_controller->all() ) {
214 if( e->gun ) {
215 item gun( e );
216 if( !gun.magazine_integral() ) {
217 gun.put_in( item( gun.magazine_default() ) );
218 }
219 gun.ammo_set( gun.ammo_default( false ), gun.ammo_capacity() );
220
221 dump( test_npcs[ "S1" ], gun );
222
223 if( gun.type->gun->barrel_length > 0_ml ) {
224 gun.put_in( item( "barrel_small" ) );
225 dump( test_npcs[ "S1" ], gun );
226 }
227 }
228 }
229
230 } else if( what == "RECIPE" ) {
231
232 // optionally filter recipes to include only those using specified skills
233 recipe_subset dict;
234 for( const auto &r : recipe_dict ) {
235 if( opts.empty() || std::any_of( opts.begin(), opts.end(), [&r]( const std::string & s ) {
236 if( r.second.skill_used == skill_id( s ) && r.second.difficulty > 0 ) {
237 return true;
238 }
239 const auto iter = r.second.required_skills.find( skill_id( s ) );
240 return iter != r.second.required_skills.end() && iter->second > 0;
241 } ) ) {
242 dict.include( &r.second );
243 }
244 }
245
246 // only consider skills that are required by at least one recipe
247 std::vector<Skill> sk;
248 std::copy_if( Skill::skills.begin(), Skill::skills.end(),
249 std::back_inserter( sk ), [&dict]( const Skill & s ) {
250 return std::any_of( dict.begin(), dict.end(), [&s]( const recipe * r ) {
251 return r->skill_used == s.ident() ||
252 r->required_skills.find( s.ident() ) != r->required_skills.end();
253 } );
254 } );
255
256 header = { "Result" };
257
258 for( const auto &e : sk ) {
259 header.push_back( e.ident().str() );
260 }
261
262 for( const recipe *e : dict ) {
263 std::vector<std::string> r;
264 r.push_back( e->result_name() );
265 for( const auto &s : sk ) {
266 if( e->skill_used == s.ident() ) {
267 r.push_back( std::to_string( e->difficulty ) );
268 } else {
269 auto iter = e->required_skills.find( s.ident() );
270 r.push_back( std::to_string( iter != e->required_skills.end() ? iter->second : 0 ) );
271 }
272 }
273 rows.push_back( r );
274 }
275
276 } else if( what == "VEHICLE" ) {
277 header = {
278 "Name", "Weight (empty)", "Weight (fueled)",
279 "Max velocity (mph)", "Safe velocity (mph)", "Acceleration (mph/turn)",
280 "Aerodynamics coeff", "Rolling coeff", "Static Drag", "Offroad %"
281 };
282 auto dump = [&rows]( const vproto_id & obj ) {
283 vehicle veh_empty( obj, 0, 0 );
284 vehicle veh_fueled( obj, 100, 0 );
285
286 std::vector<std::string> r;
287 r.push_back( veh_empty.name );
288 r.push_back( std::to_string( to_kilogram( veh_empty.total_mass() ) ) );
289 r.push_back( std::to_string( to_kilogram( veh_fueled.total_mass() ) ) );
290 r.push_back( std::to_string( veh_fueled.max_velocity() / 100 ) );
291 r.push_back( std::to_string( veh_fueled.safe_velocity() / 100 ) );
292 r.push_back( std::to_string( veh_fueled.acceleration() / 100 ) );
293 r.push_back( std::to_string( veh_fueled.coeff_air_drag() ) );
294 r.push_back( std::to_string( veh_fueled.coeff_rolling_drag() ) );
295 r.push_back( std::to_string( veh_fueled.static_drag( false ) ) );
296 r.push_back( std::to_string( static_cast<int>( 50 *
297 veh_fueled.k_traction( veh_fueled.wheel_area() ) ) ) );
298 rows.push_back( r );
299 };
300 for( auto &e : vehicle_prototype::get_all() ) {
301 dump( e );
302 }
303
304 } else if( what == "VPART" ) {
305 header = {
306 "Name", "Location", "Weight", "Size"
307 };
308 auto dump = [&rows]( const vpart_info & obj ) {
309 std::vector<std::string> r;
310 r.push_back( obj.name() );
311 r.push_back( obj.location );
312 int w = std::ceil( to_gram( item( obj.item ).weight() ) / 1000.0 );
313 r.push_back( std::to_string( w ) );
314 r.push_back( std::to_string( obj.size / units::legacy_volume_factor ) );
315 rows.push_back( r );
316 };
317 for( const auto &e : vpart_info::all() ) {
318 dump( e.second );
319 }
320
321 } else {
322 std::cerr << "unknown argument: " << what << std::endl;
323 return false;
324 }
325
326 rows.erase( std::remove_if( rows.begin(), rows.end(), []( const std::vector<std::string> &e ) {
327 return e.empty();
328 } ), rows.end() );
329
330 if( scol >= 0 ) {
331 std::sort( rows.begin(), rows.end(), [&scol]( const std::vector<std::string> &lhs,
332 const std::vector<std::string> &rhs ) {
333 return localized_compare( lhs[ scol ], rhs[ scol ] );
334 } );
335 }
336
337 rows.erase( std::unique( rows.begin(), rows.end() ), rows.end() );
338
339 switch( mode ) {
340 case dump_mode::TSV:
341 rows.insert( rows.begin(), header );
342 for( const auto &r : rows ) {
343 // NOLINTNEXTLINE(cata-text-style): using tab to align the output
344 std::copy( r.begin(), r.end() - 1, std::ostream_iterator<std::string>( std::cout, "\t" ) );
345 std::cout << r.back() << "\n";
346 }
347 break;
348
349 case dump_mode::HTML:
350 std::cout << "<table>";
351
352 std::cout << "<thead>";
353 std::cout << "<tr>";
354 for( const auto &col : header ) {
355 std::cout << "<th>" << col << "</th>";
356 }
357 std::cout << "</tr>";
358 std::cout << "</thead>";
359
360 std::cout << "<tdata>";
361 for( const auto &r : rows ) {
362 std::cout << "<tr>";
363 for( const auto &col : r ) {
364 std::cout << "<td>" << col << "</td>";
365 }
366 std::cout << "</tr>";
367 }
368 std::cout << "</tdata>";
369
370 std::cout << "</table>";
371 break;
372 }
373
374 return true;
375}
body_part get_body_part_token(const std::string &id)
Returns the matching body_part token from the corresponding body_part string.
Definition: bodypart.cpp:180
body_part
Definition: bodypart.h:41
std::string to_string(const time_duration &d)
Returns a string showing a duration.
Definition: calendar.cpp:327
Definition: skill.h:33
static std::vector< Skill > skills
Definition: skill.h:49
const skill_id & ident() const
Definition: skill.h:65
units::mass weight(bool include_contents=true, bool integral=false) const
Definition: item.cpp:4984
void put_in(const item &payload)
Puts the given item into this one, no checks are performed.
Definition: item.cpp:999
item & ammo_set(const itype_id &ammo, int qty=-1)
Filter setting the ammo for this instance Any existing ammo is removed.
Definition: item.cpp:594
std::set< constrecipe * >::const_iterator begin() const
std::set< constrecipe * >::const_iterator end() const
void include(const recipe *r, int custom_difficulty=-1)
Include a recipe to the subset.
Definition: recipe.h:35
An NPC with standard stats.
Definition: npc.h:1363
static const std::map< vitamin_id, vitamin > & all()
Get all currently loaded vitamins.
Definition: vitamin.cpp:98
static const std::map< vpart_id, vpart_info > & all()
Definition: veh_type.cpp:696
static const std::string flag_VARSIZE("VARSIZE")
std::unique_ptr< Item_factory > item_controller
void transform(player &p, const tripoint &pos)
Transform the examined object into the object specified by its transforms_into property.
Definition: iexamine.cpp:1557
void load_core_bn_modfiles()
Load & finalize modlist that consists of single vanilla BN core "mod".
Definition: init.cpp:922
int gun_engagement_moves(const Character &who, const item &gun, int target=0, int start=MAX_RECOIL)
How many moves does it take to aim gun to the target accuracy.
Definition: ranged.cpp:584
static constexpr volume legacy_volume_factor
Definition: units_volume.h:50
constexpr value_type to_gram(const quantity< value_type, mass_in_milligram_tag > &v)
Definition: units_mass.h:68
constexpr value_type to_kilogram(const quantity< value_type, mass_in_milligram_tag > &v)
Definition: units_mass.h:74
std::string enumerate_as_string(const _Container &values, enumeration_conjunction conj=enumeration_conjunction::and_)
Definition: output.h:637
recipe_dictionary recipe_dict
float total_damage() const
Definition: damage.cpp:75
std::vector< damage_unit >::iterator begin()
Definition: damage.cpp:120
bool empty() const
Definition: damage.cpp:88
Default (or randomized) charges except if counted by charges then only one charge.
Definition: item.h:230
Definition: itype.h:805
static std::vector< vproto_id > get_all()
Definition: veh_type.cpp:1158

References vitamin::all(), item::ammo_capacity(), item::ammo_default(), item::ammo_set(), damage_instance::begin(), item::covers(), damage_instance::empty(), enumerate_as_string(), flag_VARSIZE(), g, get_body_part_token(), itype::gun, ranged::gun_engagement_moves(), item::has_flag(), Skill::ident(), recipe_subset::include(), item_controller, itype_id, units::legacy_volume_factor, init::load_core_bn_modfiles(), anonymous_namespace{overmap_location.cpp}::locations, item::magazine_default(), item::magazine_integral(), none, num_bp, item::put_in(), recipe_dict, item::set_flag(), Skill::skills, units::to_gram(), to_string(), damage_instance::total_damage(), iexamine::transform(), calendar::turn, and item::type.

◆ events()

event_bus & game::events ( )

Definition at line 2714 of file game.cpp.

2715{
2716 return *event_bus_ptr;
2717}
pimpl< event_bus > event_bus_ptr
Definition: game.h:951

References event_bus_ptr.

Referenced by cleanup_at_end(), and game().

◆ exam_vehicle()

void game::exam_vehicle ( vehicle veh,
point  cp = point_zero 
)

open vehicle interaction screen

Definition at line 5002 of file game.cpp.

5003{
5004 if( veh.magic ) {
5005 add_msg( m_info, _( "This is your %s" ), veh.name );
5006 return;
5007 }
5008 auto act = veh_interact::run( veh, c );
5009 if( act ) {
5010 u.moves = 0;
5012 }
5013}
static player_activity run(vehicle &veh, point p)
bool magic
Definition: vehicle.h:1598
constexpr double c
Definition: magic.cpp:1032
activity_id act
Definition: sounds.cpp:76

References _, act, add_msg(), Character::assign_activity(), c, m_info, vehicle::magic, Creature::moves, vehicle::name, veh_interact::run(), and u.

◆ examine() [1/2]

void game::examine ( )
private

Definition at line 5393 of file game.cpp.

5394{
5395 // if we are driving a vehicle, examine the
5396 // current tile without asking.
5397 const optional_vpart_position vp = m.veh_at( u.pos() );
5398 if( vp && vp->vehicle().player_in_control( u ) ) {
5399 examine( u.pos() );
5400 return;
5401 }
5402
5403 const std::optional<tripoint> examp_ = choose_adjacent_highlight( _( "Examine where?" ),
5404 _( "There is nothing that can be examined nearby." ),
5405 ACTION_EXAMINE, false );
5406 if( !examp_ ) {
5407 return;
5408 }
5409 u.manual_examine = true;
5410 examine( *examp_ );
5411 u.manual_examine = false;
5412}
std::optional< tripoint > choose_adjacent_highlight(const std::string &message, const std::string &failure_message, const action_id action, bool allow_vertical)
Request player input of adjacent tile with highlighting, possibly on different z-level.
Definition: action.cpp:1004
@ ACTION_EXAMINE
Examine or pick up items from adjacent square.
Definition: action.h:101
void examine()
Definition: game.cpp:5393
bool manual_examine
Definition: player.h:249

References _, ACTION_EXAMINE, choose_adjacent_highlight(), examine(), m, player::manual_examine, Character::pos(), u, and map::veh_at().

Referenced by examine(), and handle_action().

◆ examine() [2/2]

void game::examine ( const tripoint p)
private

Definition at line 5481 of file game.cpp.

5482{
5483 if( disable_robot( examp ) ) {
5484 return;
5485 }
5486
5487 Creature *c = critter_at( examp );
5488 if( c != nullptr ) {
5489 monster *mon = dynamic_cast<monster *>( c );
5490 if( mon != nullptr ) {
5491 if( mon->battery_item && mon->has_effect( effect_pet ) ) {
5492 const itype &type = *mon->type->mech_battery;
5493 int max_charge = type.magazine->capacity;
5494 float charge_percent;
5495 if( mon->battery_item ) {
5496 charge_percent = static_cast<float>( mon->battery_item->ammo_remaining() ) / max_charge * 100;
5497 } else {
5498 charge_percent = 0.0;
5499 }
5500 add_msg( _( "There is a %s. Battery level: %d%%" ), mon->get_name(),
5501 static_cast<int>( charge_percent ) );
5502 } else {
5503 add_msg( _( "There is a %s." ), mon->get_name() );
5504 }
5505
5506
5507 if( mon->has_effect( effect_pet ) && !u.is_mounted() ) {
5508 if( monexamine::pet_menu( *mon ) ) {
5509 return;
5510 }
5511 } else if( mon->has_flag( MF_RIDEABLE_MECH ) && !mon->has_effect( effect_pet ) ) {
5512 if( monexamine::mech_hack( *mon ) ) {
5513 return;
5514 }
5515 } else if( mon->has_flag( MF_PAY_BOT ) ) {
5516 if( monexamine::pay_bot( *mon ) ) {
5517 return;
5518 }
5519 } else if( mon->attitude_to( u ) == Creature::A_FRIENDLY && !u.is_mounted() ) {
5520 if( monexamine::mfriend_menu( *mon ) ) {
5521 return;
5522 }
5523 }
5524 } else if( u.is_mounted() ) {
5525 add_msg( m_warning, _( "You cannot do that while mounted." ) );
5526 }
5527 npc *np = dynamic_cast<npc *>( c );
5528 if( np != nullptr && !u.is_mounted() ) {
5529 if( npc_menu( *np ) ) {
5530 return;
5531 }
5532 } else if( np != nullptr && u.is_mounted() ) {
5533 add_msg( m_warning, _( "You cannot do that while mounted." ) );
5534 }
5535 }
5536
5537 const optional_vpart_position vp = m.veh_at( examp );
5538 if( vp && u.is_mounted() ) {
5539 if( !u.mounted_creature->has_flag( MF_RIDEABLE_MECH ) ) {
5540 add_msg( m_warning, _( "You cannot interact with a vehicle while mounted." ) );
5541 } else {
5542 vp->vehicle().interact_with( examp, vp->part_index() );
5543 return;
5544 }
5545 } else if( vp && !u.is_mounted() ) {
5546 vp->vehicle().interact_with( examp, vp->part_index() );
5547 return;
5548 }
5549
5550 if( m.has_flag( "CONSOLE", examp ) && !u.is_mounted() ) {
5551 use_computer( examp );
5552 return;
5553 } else if( m.has_flag( "CONSOLE", examp ) && u.is_mounted() ) {
5554 add_msg( m_warning, _( "You cannot use a console while mounted." ) );
5555 }
5556 const furn_t &xfurn_t = m.furn( examp ).obj();
5557 const ter_t &xter_t = m.ter( examp ).obj();
5558
5559 const tripoint player_pos = u.pos();
5560
5561 if( m.has_furn( examp ) && !u.is_mounted() ) {
5562 xfurn_t.examine( u, examp );
5563 } else if( m.has_furn( examp ) && u.is_mounted() ) {
5564 add_msg( m_warning, _( "You cannot do that while mounted." ) );
5565 } else {
5566 if( !u.is_mounted() ) {
5567 xter_t.examine( u, examp );
5568 } else if( u.is_mounted() && xter_t.examine == &iexamine::none ) {
5569 xter_t.examine( u, examp );
5570 } else {
5571 add_msg( m_warning, _( "You cannot do that while mounted." ) );
5572 }
5573 }
5574
5575 // Did the player get moved? Bail out if so; our examp probably
5576 // isn't valid anymore.
5577 if( player_pos != u.pos() ) {
5578 return;
5579 }
5580
5581 bool none = true;
5582 if( xter_t.examine != &iexamine::none || xfurn_t.examine != &iexamine::none ) {
5583 none = false;
5584 }
5585
5586 if( !m.tr_at( examp ).is_null() && !u.is_mounted() ) {
5587 iexamine::trap( u, examp );
5588 } else if( !m.tr_at( examp ).is_null() && u.is_mounted() ) {
5589 add_msg( m_warning, _( "You cannot do that while mounted." ) );
5590 }
5591
5592 // In case of teleport trap or somesuch
5593 if( player_pos != u.pos() ) {
5594 return;
5595 }
5596
5597 // Feedback for fire lasting time, this can be judged while mounted
5598 const std::string fire_fuel = get_fire_fuel_string( examp );
5599 if( !fire_fuel.empty() ) {
5600 add_msg( fire_fuel );
5601 }
5602
5603 if( m.has_flag( "SEALED", examp ) ) {
5604 if( none ) {
5605 if( m.has_flag( "UNSTABLE", examp ) ) {
5606 add_msg( _( "The %s is too unstable to remove anything." ), m.name( examp ) );
5607 } else {
5608 add_msg( _( "The %s is firmly sealed." ), m.name( examp ) );
5609 }
5610 }
5611 } else {
5612 //examp has no traps, is a container and doesn't have a special examination function
5613 if( m.tr_at( examp ).is_null() && m.i_at( examp ).empty() &&
5614 m.has_flag( "CONTAINER", examp ) && none ) {
5615 add_msg( _( "It is empty." ) );
5616 } else if( ( m.has_flag( TFLAG_FIRE_CONTAINER, examp ) &&
5617 xfurn_t.examine == &iexamine::fireplace ) ||
5618 xfurn_t.examine == &iexamine::workbench ||
5619 xfurn_t.examine == &iexamine::transform ) {
5620 return;
5621 } else {
5623 if( !u.is_mounted() ) {
5624 pickup::pick_up( examp, 0 );
5625 }
5626 }
5627 }
5628}
shared_ptr_fast< monster > mounted_creature
Definition: character.h:1617
@ A_FRIENDLY
Definition: creature.h:169
void use_computer(const tripoint &p)
Checks to see if a player can use a computer (not illiterate, etc.) and uses if able.
Definition: game.cpp:4513
bool disable_robot(const tripoint &p)
If there is a robot (that can be disabled), query the player and try to disable it.
Definition: game.cpp:8658
bool npc_menu(npc &who)
Returns true if the menu handled stuff and player shouldn't do anything else.
Definition: game.cpp:5284
bool empty() const
Definition: item_stack.cpp:15
bool has_furn(const tripoint &p) const
Definition: map.cpp:1408
const trap & tr_at(const tripoint &p) const
Definition: map.cpp:5258
ter_id ter(const tripoint &p) const
Definition: map.cpp:1563
Attitude attitude_to(const Creature &other) const override
Attitude (of this creature) towards another creature.
Definition: monster.cpp:1045
cata::value_ptr< item > battery_item
Definition: monster.h:465
std::string get_name() const override
Definition: monster.cpp:484
static std::string get_fire_fuel_string(const tripoint &examp)
Definition: game.cpp:5414
@ TFLAG_FIRE_CONTAINER
Definition: mapdata.h:294
void fireplace(player &p, const tripoint &examp)
Definition: iexamine.cpp:2834
void workbench(player &p, const tripoint &examp)
Definition: iexamine.cpp:6139
void none(player &p, const tripoint &examp)
Nothing player can interact with here.
Definition: iexamine.cpp:253
void trap(player &p, const tripoint &examp)
Definition: iexamine.cpp:3733
bool pet_menu(monster &z)
Definition: monexamine.cpp:67
bool mech_hack(monster &z)
Definition: monexamine.cpp:433
bool mfriend_menu(monster &z)
Definition: monexamine.cpp:507
bool pay_bot(monster &z)
Definition: monexamine.cpp:466
void pick_up(const tripoint &p, int min, from_where get_items_from=prompt)
Pick up items; 'g' or ',' or via examine()
Definition: pickup.cpp:576
iexamine_function examine
Definition: mapdata.h:404
itype_id mech_battery
If this monster is a rideable mech it needs a power source battery type.
Definition: mtype.h:372
Definition: mapdata.h:463
bool is_null() const
Whether this is the null-traps, aka no trap at all.
Definition: trap.cpp:245

References _, Creature::A_FRIENDLY, add_msg(), monster::attitude_to(), monster::battery_item, c, critter_at(), disable_robot(), effect_pet, item_stack::empty(), map_data_common_t::examine, iexamine::fireplace(), map::furn(), get_fire_fuel_string(), monster::get_name(), Creature::has_effect(), map::has_flag(), monster::has_flag(), map::has_furn(), map::i_at(), Character::is_mounted(), trap::is_null(), m, m_warning, mtype::mech_battery, monexamine::mech_hack(), MF_PAY_BOT, MF_RIDEABLE_MECH, monexamine::mfriend_menu(), Character::mounted_creature, map::name(), none, iexamine::none(), npc_menu(), int_id< T >::obj(), monexamine::pay_bot(), monexamine::pet_menu(), pickup::pick_up(), Character::pos(), sounds::process_sound_markers(), map::ter(), TFLAG_FIRE_CONTAINER, map::tr_at(), iexamine::transform(), iexamine::trap(), type, monster::type, u, use_computer(), map::veh_at(), and iexamine::workbench().

◆ extended_description()

void game::extended_description ( const tripoint p)

Long description of (visible) things at tile.

Definition at line 51 of file descriptions.cpp.

52{
54 const int top = 3;
55 int width = 0;
56 catacurses::window w_head;
57 catacurses::window w_main;
58 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
59 const int left = 0;
60 const int right = TERMX;
61 const int bottom = TERMY;
62 width = right - left;
63 const int height = bottom - top;
64 w_head = catacurses::newwin( top, TERMX, point_zero );
65 w_main = catacurses::newwin( height, width, point( left, top ) );
66 ui.position( point_zero, point( TERMX, TERMY ) );
67 } );
68 ui.mark_resize();
69
70 // Default to critter (if any), furniture (if any), then terrain.
72 if( seen_critter( *this, p ) != nullptr ) {
74 } else if( get_map().has_furn( p ) ) {
76 }
77
78 std::string action;
79 input_context ctxt( "EXTENDED_DESCRIPTION" );
80 ctxt.register_action( "CREATURE" );
81 ctxt.register_action( "FURNITURE" );
82 ctxt.register_action( "TERRAIN" );
83 ctxt.register_action( "CONFIRM" );
84 ctxt.register_action( "QUIT" );
85 ctxt.register_action( "HELP_KEYBINDINGS" );
86
87 ui.on_redraw( [&]( const ui_adaptor & ) {
88 werase( w_head );
90 _( "[%s] describe creatures, [%s] describe furniture, "
91 "[%s] describe terrain, [%s] close." ),
92 ctxt.get_desc( "CREATURE" ), ctxt.get_desc( "FURNITURE" ),
93 ctxt.get_desc( "TERRAIN" ), ctxt.get_desc( "QUIT" ) );
94
95 // Set up line drawings
96 for( int i = 0; i < TERMX; i++ ) {
97 mvwputch( w_head, point( i, top - 1 ), c_white, LINE_OXOX );
98 }
99
100 wnoutrefresh( w_head );
101
102 std::string desc;
103 // Allow looking at invisible tiles - player may want to examine hallucinations etc.
104 switch( cur_target ) {
106 const Creature *critter = seen_critter( *this, p );
107 if( critter != nullptr ) {
108 desc = critter->extended_description();
109 } else {
110 desc = _( "You do not see any creature here." );
111 }
112 }
113 break;
115 if( !u.sees( p ) || !m.has_furn( p ) ) {
116 desc = _( "You do not see any furniture here." );
117 } else {
118 const furn_id fid = m.furn( p );
119 if( display_mod_source ) {
120 const std::string mod_src = enumerate_as_string( fid->src.begin(),
121 fid->src.end(), []( const std::pair<furn_str_id, mod_id> &source ) {
122 return string_format( "'%s'", source.second->name() );
124 desc = string_format( _( "Origin: %s\n" ), mod_src );
125 }
126 if( display_object_ids ) {
127 desc += colorize( string_format( "[%s]\n", fid.id() ), c_light_blue );
128 }
129 desc += fid.obj().extended_description();
130 }
131 break;
133 if( !u.sees( p ) ) {
134 desc = _( "You can't see the terrain here." );
135 } else {
136 const ter_id tid = m.ter( p );
137 if( display_mod_source ) {
138 const std::string mod_src = enumerate_as_string( tid->src.begin(),
139 tid->src.end(), []( const std::pair<ter_str_id, mod_id> &source ) {
140 return string_format( "'%s'", source.second->name() );
142 desc = string_format( _( "Origin: %s\n" ), mod_src );
143 }
144 if( display_object_ids ) {
145 desc += colorize( string_format( "[%s]\n", tid.id() ), c_light_blue );
146 }
147 desc += tid.obj().extended_description();
148 }
149 break;
150 }
151
152 std::string signage = m.get_signage( p );
153 if( !signage.empty() ) {
154 // NOLINTNEXTLINE(cata-text-style): the question mark does not end a sentence
155 desc += u.has_trait( trait_ILLITERATE ) ? _( "\nSign: ???" ) : string_format( _( "\nSign: %s" ),
156 signage );
157 }
158
159 werase( w_main );
160 fold_and_print_from( w_main, point_zero, width, 0, c_light_gray, desc );
161 wnoutrefresh( w_main );
162 } );
163
164 do {
166 action = ctxt.handle_input();
167 if( action == "CREATURE" ) {
168 cur_target = description_target::creature;
169 } else if( action == "FURNITURE" ) {
171 } else if( action == "TERRAIN" ) {
172 cur_target = description_target::terrain;
173 }
174 } while( action != "CONFIRM" && action != "QUIT" );
175}
bool display_object_ids
Display internal IDs for items, furniture, terrain and monsters.
bool display_mod_source
Display mod source for items, furniture, terrain and monsters.
virtual std::string extended_description() const =0
const string_id< T > & id() const
Definition: ammo_effect.cpp:33
std::string get_signage(const tripoint &p) const
Definition: map.cpp:4120
std::string colorize(const std::string &text, const nc_color &color)
Definition: color.cpp:669
static const trait_id trait_ILLITERATE("ILLITERATE")
static const Creature * seen_critter(const game &g, const tripoint &p)
description_target
int fold_and_print_from(const catacurses::window &w, point begin, int width, int begin_line, const nc_color &base_color, const std::string &text)
Like fold_and_print, but starts the output with the N-th line of the folded string.
Definition: output.cpp:311
std::vector< std::pair< furn_str_id, mod_id > > src
Definition: mapdata.h:502
std::string extended_description() const
std::vector< std::pair< ter_str_id, mod_id > > src
Definition: mapdata.h:465

References _, action, arrow, c_light_blue, c_light_gray, c_white, colorize(), creature, display_mod_source, display_object_ids, enumerate_as_string(), map_data_common_t::extended_description(), Creature::extended_description(), fold_and_print_from(), map::furn(), furniture, input_context::get_desc(), get_map, map::get_signage(), input_context::handle_input(), map::has_furn(), Character::has_trait(), int_id< T >::id(), left, LINE_OXOX, m, mvwprintz(), mvwputch(), catacurses::newwin(), int_id< T >::obj(), point_zero, ui_manager::redraw(), input_context::register_action(), right, seen_critter(), Character::sees(), ter_t::src, furn_t::src, string_format(), map::ter(), TERMX, TERMY, terrain, trait_ILLITERATE, u, catacurses::werase(), and catacurses::wnoutrefresh().

Referenced by look_around().

◆ find_nearby_items()

std::vector< map_item_stack > game::find_nearby_items ( int  iRadius)
private

Definition at line 6952 of file game.cpp.

6953{
6954 std::map<std::string, map_item_stack> temp_items;
6955 std::vector<map_item_stack> ret;
6956 std::vector<std::string> item_order;
6957
6958 if( u.is_blind() ) {
6959 return ret;
6960 }
6961
6962 int range = fov_3d ? ( fov_3d_z_range * 2 ) + 1 : 1;
6963 int center_z = u.pos().z;
6964
6965 for( int i = 1; i <= range; i++ ) {
6966 int z = i % 2 ? center_z - i / 2 : center_z + i / 2;
6967 for( auto &points_p_it : closest_points_first( {u.pos().xy(), z}, iRadius ) ) {
6968 if( points_p_it.y >= u.posy() - iRadius && points_p_it.y <= u.posy() + iRadius &&
6969 u.sees( points_p_it ) &&
6970 m.sees_some_items( points_p_it, u ) ) {
6971
6972 for( auto &elem : m.i_at( points_p_it ) ) {
6973 const std::string name = elem.tname();
6974 const tripoint relative_pos = points_p_it - u.pos();
6975
6976 if( std::find( item_order.begin(), item_order.end(), name ) == item_order.end() ) {
6977 item_order.push_back( name );
6978 temp_items[name] = map_item_stack( &elem, relative_pos );
6979 } else {
6980 temp_items[name].add_at_pos( &elem, relative_pos );
6981 }
6982 }
6983 }
6984 }
6985 }
6986
6987 for( auto &elem : item_order ) {
6988 ret.push_back( temp_items[elem] );
6989 }
6990
6991 return ret;
6992}
int fov_3d_z_range
3D FoV range, in Z levels, in both directions.
bool fov_3d
3D FoV enabled/disabled.
@ range
Definition: character.h:104
bool is_blind() const
Returns true if the player isn't able to see.
Definition: character.cpp:6275
std::vector< coords::coord_point< Point, Origin, Scale > > closest_points_first(const coords::coord_point< Point, Origin, Scale > &loc, int min_dist, int max_dist)
Definition: coordinates.h:596

References closest_points_first(), detail::find(), fov_3d, fov_3d_z_range, map::i_at(), Character::is_blind(), m, om_direction::name(), Character::pos(), Character::posy(), range, cata::hash64_detail::ret, Character::sees(), map::sees_some_items(), u, and tripoint::z.

Referenced by list_items_monsters().

◆ find_npc()

npc * game::find_npc ( character_id  id)

Find the npc with the given ID.

Returns NULL if the npc could not be found. Searches all loaded overmaps.

Definition at line 1870 of file game.cpp.

1871{
1872 return overmap_buffer.find_npc( id ).get();
1873}

References overmapbuffer::find_npc(), and overmap_buffer.

Referenced by critter_by_id().

◆ find_or_make_stairs()

std::optional< tripoint > game::find_or_make_stairs ( map mp,
int  z_after,
bool &  rope_ladder,
bool  peeking 
)

Returns the other end of the stairs (if any).

May query, affect u etc.

Definition at line 10462 of file game.cpp.

10464{
10465 const int omtilesz = SEEX * 2;
10466 real_coords rc( m.getabs( point( u.posx(), u.posy() ) ) );
10467 tripoint omtile_align_start( m.getlocal( rc.begin_om_pos() ), z_after );
10468 tripoint omtile_align_end( omtile_align_start + point( -1 + omtilesz, -1 + omtilesz ) );
10469
10470 // Try to find the stairs.
10471 std::optional<tripoint> stairs;
10472 int best = INT_MAX;
10473 const int movez = z_after - get_levz();
10474 const bool going_down_1 = movez == -1;
10475 const bool going_up_1 = movez == 1;
10476 // If there are stairs on the same x and y as we currently are, use those
10477 if( going_down_1 && mp.has_flag( TFLAG_GOES_UP, u.pos() + tripoint_below ) ) {
10478 stairs.emplace( u.pos() + tripoint_below );
10479 }
10480 if( going_up_1 && mp.has_flag( TFLAG_GOES_DOWN, u.pos() + tripoint_above ) ) {
10481 stairs.emplace( u.pos() + tripoint_above );
10482 }
10483 // We did not find stairs directly above or below, so search the map for them
10484 if( !stairs.has_value() ) {
10485 for( const tripoint &dest : m.points_in_rectangle( omtile_align_start, omtile_align_end ) ) {
10486 if( rl_dist( u.pos(), dest ) <= best &&
10487 ( ( going_down_1 && mp.has_flag( TFLAG_GOES_UP, dest ) ) ||
10488 ( going_up_1 && ( mp.has_flag( TFLAG_GOES_DOWN, dest ) ||
10489 mp.ter( dest ) == t_manhole_cover ) ) ||
10490 ( ( movez == 2 || movez == -2 ) && mp.ter( dest ) == t_elevator ) ) ) {
10491 stairs.emplace( dest );
10492 best = rl_dist( u.pos(), dest );
10493 }
10494 }
10495 }
10496
10497 if( stairs.has_value() ) {
10498 if( Creature *blocking_creature = critter_at( stairs.value() ) ) {
10499 npc *guy = dynamic_cast<npc *>( blocking_creature );
10500 monster *mon = dynamic_cast<monster *>( blocking_creature );
10501 bool would_move = ( guy && !guy->is_enemy() ) || ( mon && mon->friendly == -1 );
10502 bool can_displace = find_empty_spot_nearby( *stairs ).has_value();
10503 std::string cr_name = blocking_creature->get_name();
10504 std::string msg;
10505 if( guy ) {
10506 //~ %s is the name of hostile NPC
10507 msg = string_format( _( "%s is in the way!" ), cr_name );
10508 } else {
10509 //~ %s is some monster
10510 msg = string_format( _( "There's a %s in the way!" ), cr_name );
10511 }
10512
10513 if( ( peeking && !would_move ) || !can_displace || ( !would_move && !query_yn(
10514 //~ %s is a warning about monster/hostile NPC in the way, e.g. "There's a zombie in the way!"
10515 _( "%s Attempt to push past? You may have to fight your way back up." ), msg ) ) ) {
10516 add_msg( msg );
10517 return std::nullopt;
10518 }
10519 }
10520 return stairs;
10521 }
10522
10523 // No stairs found! Try to make some
10524 rope_ladder = false;
10525 stairs.emplace( u.pos() );
10526 stairs->z = z_after;
10527 // Check the destination area for lava.
10528 if( mp.ter( *stairs ) == t_lava ) {
10529 if( movez < 0 &&
10530 !query_yn(
10531 _( "There is a LOT of heat coming out of there, even the stairs have melted away. Jump down? You won't be able to get back up." ) ) ) {
10532 return std::nullopt;
10533 } else if( movez > 0 &&
10534 !query_yn(
10535 _( "There is a LOT of heat coming out of there. Push through the half-molten rocks and ascend? You will not be able to get back down." ) ) ) {
10536 return std::nullopt;
10537 }
10538
10539 return stairs;
10540 }
10541
10542 if( movez > 0 ) {
10543 if( !mp.has_flag( "GOES_DOWN", *stairs ) ) {
10544 if( !query_yn( _( "You may be unable to return back down these stairs. Continue up?" ) ) ) {
10545 return std::nullopt;
10546 }
10547 }
10548 // Manhole covers need this to work
10549 // Maybe require manhole cover here and fail otherwise?
10550 return stairs;
10551 }
10552
10553 if( mp.impassable( *stairs ) ) {
10554 popup( _( "Halfway down, the way down becomes blocked off." ) );
10555 return std::nullopt;
10556 }
10557
10558 if( u.has_trait( trait_id( "WEB_RAPPEL" ) ) ) {
10559 if( query_yn( _( "There is a sheer drop halfway down. Web-descend?" ) ) ) {
10560 rope_ladder = true;
10561 if( ( rng( 4, 8 ) ) < u.get_skill_level( skill_dodge ) ) {
10562 add_msg( _( "You attach a web and dive down headfirst, flipping upright and landing on your feet." ) );
10563 } else {
10564 add_msg( _( "You securely web up and work your way down, lowering yourself safely." ) );
10565 }
10566 } else {
10567 return std::nullopt;
10568 }
10569 } else if( u.has_trait( trait_VINES2 ) || u.has_trait( trait_VINES3 ) ) {
10570 if( query_yn( _( "There is a sheer drop halfway down. Use your vines to descend?" ) ) ) {
10571 if( u.has_trait( trait_VINES2 ) ) {
10572 if( query_yn( _( "Detach a vine? It'll hurt, but you'll be able to climb back up…" ) ) ) {
10573 rope_ladder = true;
10574 add_msg( m_bad, _( "You descend on your vines, though leaving a part of you behind stings." ) );
10575 u.mod_pain( 5 );
10576 u.apply_damage( nullptr, bodypart_id( "torso" ), 5 );
10577 u.mod_stored_nutr( 10 );
10578 u.mod_thirst( 10 );
10579 } else {
10580 add_msg( _( "You gingerly descend using your vines." ) );
10581 }
10582 } else {
10583 add_msg( _( "You effortlessly lower yourself and leave a vine rooted for future use." ) );
10584 rope_ladder = true;
10585 u.mod_stored_nutr( 10 );
10586 u.mod_thirst( 10 );
10587 }
10588 } else {
10589 return std::nullopt;
10590 }
10591 } else if( u.has_amount( itype_grapnel, 1 ) ) {
10592 if( query_yn( _( "There is a sheer drop halfway down. Climb your grappling hook down?" ) ) ) {
10593 rope_ladder = true;
10595 } else {
10596 return std::nullopt;
10597 }
10598 } else if( u.has_amount( itype_rope_30, 1 ) ) {
10599 if( query_yn( _( "There is a sheer drop halfway down. Climb your rope down?" ) ) ) {
10600 rope_ladder = true;
10602 } else {
10603 return std::nullopt;
10604 }
10605 } else if( !query_yn( _( "There is a sheer drop halfway down. Jump?" ) ) ) {
10606 return std::nullopt;
10607 }
10608
10609 return stairs;
10610}
int_id< body_part_type > bodypart_id
Definition: bodypart.h:25
void mod_pain(int npain) override
Modifies a pain value by player traits before passing it to Creature::mod_pain()
Definition: character.cpp:765
void apply_damage(Creature *source, bodypart_id hurt, int dam, bool bypass_med=false) override
Actually hurt the player, hurts a body_part directly, no armor reduction.
Definition: character.cpp:8403
std::list< item > use_amount(itype_id it, int quantity, const std::function< bool(const item &)> &filter=return_true< item >)
Definition: character.cpp:9632
virtual void mod_thirst(int nthirst)
Definition: character.cpp:4439
virtual void mod_stored_nutr(int nnutr)
Definition: character.cpp:4329
int get_skill_level(const skill_id &ident) const
Definition: character.cpp:3350
tripoint getlocal(const tripoint &p) const
Inverse of getabs.
Definition: map.cpp:8417
bool impassable(const tripoint &p) const
Definition: map.cpp:1860
tripoint_range< tripoint > points_in_rectangle(const tripoint &from, const tripoint &to) const
Definition: map.cpp:8752
bool is_enemy() const
Definition: npc.cpp:2048
static const trait_id trait_VINES2("VINES2")
static const skill_id skill_dodge("dodge")
static std::optional< tripoint > find_empty_spot_nearby(const tripoint &pos)
Definition: game.cpp:9997
static const itype_id itype_rope_30("rope_30")
static const itype_id itype_grapnel("grapnel")
static const trait_id trait_VINES3("VINES3")
ter_id t_manhole_cover
Definition: mapdata.cpp:723
ter_id t_lava
Definition: mapdata.cpp:698
ter_id t_elevator
Definition: mapdata.cpp:726
@ TFLAG_GOES_DOWN
Definition: mapdata.h:309
@ TFLAG_GOES_UP
Definition: mapdata.h:310
auto dest(const elevator::tiles &elevator_here, const tripoint &sm_orig, int turns, int movez) -> elevator::tiles
static constexpr tripoint tripoint_below
Definition: point.h:281
static constexpr tripoint tripoint_above
Definition: point.h:280

References _, add_msg(), Character::apply_damage(), real_coords::begin_om_pos(), critter_at(), anonymous_namespace{iexamine_elevator.cpp}::elevator::dest(), find_empty_spot_nearby(), monster::friendly, get_levz(), Character::get_skill_level(), map::getabs(), map::getlocal(), visitable< T >::has_amount(), map::has_flag(), Character::has_trait(), map::impassable(), npc::is_enemy(), itype_grapnel, itype_rope_30, m, m_bad, Character::mod_pain(), Character::mod_stored_nutr(), Character::mod_thirst(), map::points_in_rectangle(), popup(), Character::pos(), Character::posx(), Character::posy(), query_yn(), rl_dist(), rng(), SEEX, skill_dodge, string_format(), t_elevator, t_lava, t_manhole_cover, map::ter(), TFLAG_GOES_DOWN, TFLAG_GOES_UP, trait_VINES2, trait_VINES3, tripoint_above, tripoint_below, u, and Character::use_amount().

Referenced by vertical_move().

◆ fling_creature()

void game::fling_creature ( Creature c,
const units::angle dir,
float  flvel,
bool  controlled = false 
)

Flings the input creature in the given direction.

Definition at line 9800 of file game.cpp.

9801{
9802 if( c == nullptr ) {
9803 debugmsg( "game::fling_creature invoked on null target" );
9804 return;
9805 }
9806
9807 if( c->is_dead_state() ) {
9808 // Flinging a corpse causes problems, don't enable without testing
9809 return;
9810 }
9811
9812 if( c->is_hallucination() ) {
9813 // Don't fling hallucinations
9814 return;
9815 }
9816
9817 bool thru = true;
9818 const bool is_u = ( c == &u );
9819 // Don't animate critters getting bashed if animations are off
9820 const bool animate = is_u || get_option<bool>( "ANIMATIONS" );
9821
9822 player *p = dynamic_cast<player *>( c );
9823
9824 tileray tdir( dir );
9825 int range = flvel / 10;
9826 tripoint pt = c->pos();
9827 tripoint prev_point = pt;
9828 bool force_next = false;
9829 tripoint next_forced;
9830 while( range > 0 ) {
9831 c->set_underwater( false );
9832 // TODO: Check whenever it is actually in the viewport
9833 // or maybe even just redraw the changed tiles
9834 bool seen = is_u || u.sees( *c ); // To avoid redrawing when not seen
9835 if( force_next ) {
9836 pt = next_forced;
9837 force_next = false;
9838 } else {
9839 tdir.advance();
9840 pt.x = c->posx() + tdir.dx();
9841 pt.y = c->posy() + tdir.dy();
9842 }
9843 float force = 0;
9844
9845 if( m.obstructed_by_vehicle_rotation( prev_point, pt ) ) {
9846 //We process the intervening tile on this iteration and then the current tile on the next
9847 next_forced = pt;
9848 force_next = true;
9849 if( one_in( 2 ) ) {
9850 pt.x = prev_point.x;
9851 } else {
9852 pt.y = prev_point.y;
9853 }
9854 }
9855
9856
9857 if( monster *const mon_ptr = critter_at<monster>( pt ) ) {
9858 monster &critter = *mon_ptr;
9859 // Approximate critter's "stopping power" with its max hp
9860 force = std::min<float>( 1.5f * critter.type->hp, flvel );
9861 const int damage = rng( force, force * 2.0f ) / 6;
9862 c->impact( damage, pt );
9863 // Multiply zed damage by 6 because no body parts
9864 const int zed_damage = std::max( 0,
9865 ( damage - critter.get_armor_bash( bodypart_id( "torso" ) ) ) * 6 );
9866 // TODO: Pass the "flinger" here - it's not the flung critter that deals damage
9867 critter.apply_damage( c, bodypart_id( "torso" ), zed_damage );
9868 critter.check_dead_state();
9869 if( !critter.is_dead() ) {
9870 thru = false;
9871 }
9872 } else if( m.impassable( pt ) ) {
9873 if( !m.veh_at( pt ).obstacle_at_part() ) {
9874 force = std::min<float>( m.bash_strength( pt ), flvel );
9875 } else {
9876 // No good way of limiting force here
9877 // Keep it 1 less than maximum to make the impact hurt
9878 // but to keep the target flying after it
9879 force = flvel - 1;
9880 }
9881 const int damage = rng( force, force * 2.0f ) / 9;
9882 c->impact( damage, pt );
9883 if( m.is_bashable( pt ) ) {
9884 // Only go through if we successfully make the tile passable
9885 m.bash( pt, flvel );
9886 thru = m.passable( pt );
9887 } else {
9888 thru = false;
9889 }
9890 }
9891
9892 // If the critter dies during flinging, moving it around causes debugmsgs
9893 if( c->is_dead_state() ) {
9894 return;
9895 }
9896
9897 flvel -= force;
9898 if( thru ) {
9899 if( p != nullptr ) {
9900 if( p->in_vehicle ) {
9901 m.unboard_vehicle( p->pos() );
9902 }
9903 // If we're flinging the player around, make sure the map stays centered on them.
9904 if( is_u ) {
9905 update_map( pt.x, pt.y );
9906 } else {
9907 p->setpos( pt );
9908 }
9909 } else if( !critter_at( pt ) ) {
9910 // Dying monster doesn't always leave an empty tile (blob spawning etc.)
9911 // Just don't setpos if it happens - next iteration will do so
9912 // or the monster will stop a tile before the unpassable one
9913 c->setpos( pt );
9914 }
9915 } else {
9916 // Don't zero flvel - count this as slamming both the obstacle and the ground
9917 // although at lower velocity
9918 break;
9919 }
9920 //Vehicle wall tiles don't count for range
9921 if( !force_next ) {
9922 range--;
9923 }
9924 prev_point = pt;
9925 if( animate && ( seen || u.sees( *c ) ) ) {
9930 }
9931 }
9932
9933 // Fall down to the ground - always on the last reached tile
9934 if( !m.has_flag( "SWIMMABLE", c->pos() ) ) {
9935 const trap_id trap_under_creature = m.tr_at( c->pos() ).loadid;
9936 // Didn't smash into a wall or a floor so only take the fall damage
9937 if( thru && trap_under_creature == tr_ledge ) {
9938 m.creature_on_trap( *c, false );
9939 } else {
9940 // Fall on ground
9941 int force = rng( flvel, flvel * 2 ) / 9;
9942 if( controlled ) {
9943 force = std::max( force / 2 - 5, 0 );
9944 }
9945 if( force > 0 ) {
9946 int dmg = c->impact( force, c->pos() );
9947 // TODO: Make landing damage the floor
9948 m.bash( c->pos(), dmg / 4, false, false, false );
9949 }
9950 // Always apply traps to creature i.e. bear traps, tele traps etc.
9951 m.creature_on_trap( *c, false );
9952 }
9953 } else {
9954 c->set_underwater( true );
9955 if( is_u ) {
9956 if( controlled ) {
9957 add_msg( _( "You dive into water." ) );
9958 } else {
9959 add_msg( m_warning, _( "You fall into water." ) );
9960 }
9961 }
9962 }
9963}
void setpos(const tripoint &p) override
Definition: character.h:815
void check_dead_state()
This function checks the creatures is_dead_state and (if true) calls die.
Definition: creature.cpp:1899
point update_map(player &p)
Definition: game.cpp:10689
void pump_events()
Resize & refresh if necessary, process all pending window events, and ignore keypresses.
int bash_strength(const tripoint &p, bool allow_floor=false) const
Returns max_str of the furniture or terrain at p.
Definition: map.cpp:2543
bool obstructed_by_vehicle_rotation(const tripoint &from, const tripoint &to) const
Checks if a rotated vehicle is blocking diagonal movement, tripoints must be adjacent.
Definition: map.cpp:6623
bash_results bash(const tripoint &p, int str, bool silent=false, bool destroy=false, bool bash_floor=false, const vehicle *bashing_vehicle=nullptr)
Returns a pair where first is whether anything was smashed and second is if it was destroyed.
Definition: map.cpp:3624
void unboard_vehicle(const vpart_reference &, Character *passenger, bool dead_passenger=false)
Definition: map.cpp:1146
bool is_bashable(const tripoint &p, bool allow_floor=false) const
Returns true if there is a bashable vehicle part or the furn/terrain is bashable at p.
Definition: map.cpp:2507
void creature_on_trap(Creature &critter, bool may_avoid=true)
Apply trap effects to the creature, similar to creature_in_field.
Definition: map.cpp:8629
bool passable(const tripoint &p) const
Definition: map.cpp:1865
int get_armor_bash(bodypart_id bp) const override
Definition: monster.cpp:1910
bool is_dead() const
Definition: monster.cpp:2820
void apply_damage(Creature *source, bodypart_id bp, int dam, bool bypass_med=false) override
Definition: monster.cpp:1691
std::optional< vpart_reference > obstacle_at_part() const
Definition: vehicle.cpp:2495
Definition: player.h:84
static const trap_str_id tr_ledge("tr_ledge")
void redraw_invalidated()
Redraw all invalidated windows without invalidating the top window.
Definition: ui_manager.cpp:394
int hp
Definition: mtype.h:270
trap_id loadid
Definition: trap.h:88
int y
Definition: point.h:137
int x
Definition: point.h:136

References _, add_msg(), tileray::advance(), monster::apply_damage(), map::bash(), map::bash_strength(), c, Creature::check_dead_state(), map::creature_on_trap(), critter_at(), debugmsg, tileray::dx(), tileray::dy(), monster::get_armor_bash(), map::has_flag(), mtype::hp, map::impassable(), Character::in_vehicle, inp_mngr, invalidate_main_ui_adaptor(), map::is_bashable(), monster::is_dead(), trap::loadid, m, m_warning, optional_vpart_position::obstacle_at_part(), map::obstructed_by_vehicle_rotation(), one_in(), map::passable(), Character::pos(), input_manager::pump_events(), range, ui_manager::redraw_invalidated(), refresh_display(), rng(), Character::sees(), Character::setpos(), map::tr_at(), tr_ledge, monster::type, u, map::unboard_vehicle(), update_map(), map::veh_at(), tripoint::x, and tripoint::y.

Referenced by moving_vehicle_dismount().

◆ forced_door_closing()

bool game::forced_door_closing ( const tripoint p,
const ter_id door_type,
int  bash_dmg 
)

Definition at line 5015 of file game.cpp.

5016{
5017 const auto valid_location = [&]( const tripoint & p ) {
5018 return g->is_empty( p );
5019 };
5020 const auto get_random_point = [&]() -> tripoint {
5021 if( auto pos = random_point( m.points_in_radius( p, 2 ), valid_location ) )
5022 {
5023 return p * 2 - ( *pos );
5024 } else
5025 {
5026 return p;
5027 }
5028 };
5029
5030 const std::string &door_name = door_type.obj().name();
5031 const tripoint kbp = get_random_point();
5032
5033 // can't pushback any creatures/items anywhere, that means the door can't close.
5034 const bool cannot_push = kbp == p;
5035 const bool can_see = u.sees( p );
5036
5037 player *npc_or_player = critter_at<player>( p, false );
5038 if( npc_or_player != nullptr ) {
5039 if( bash_dmg <= 0 ) {
5040 return false;
5041 }
5042 if( npc_or_player->is_npc() && can_see ) {
5043 add_msg( _( "The %1$s hits the %2$s." ), door_name, npc_or_player->name );
5044 } else if( npc_or_player->is_player() ) {
5045 add_msg( m_bad, _( "The %s hits you." ), door_name );
5046 }
5047 if( npc_or_player->activity ) {
5048 npc_or_player->cancel_activity();
5049 }
5050 // TODO: make the npc angry?
5051 npc_or_player->hitall( bash_dmg, 0, nullptr );
5052 if( cannot_push ) {
5053 return false;
5054 }
5055 // TODO implement who was closing the door and replace nullptr
5056 knockback( kbp, p, std::max( 1, bash_dmg / 10 ), -1, 1, nullptr );
5057 // TODO: perhaps damage/destroy the gate
5058 // if the npc was really big?
5059 }
5060 if( monster *const mon_ptr = critter_at<monster>( p ) ) {
5061 monster &critter = *mon_ptr;
5062 if( bash_dmg <= 0 ) {
5063 return false;
5064 }
5065 if( can_see ) {
5066 add_msg( _( "The %1$s hits the %2$s." ), door_name, critter.name() );
5067 }
5068 if( critter.type->size <= MS_SMALL ) {
5069 critter.die_in_explosion( nullptr );
5070 } else {
5071 critter.apply_damage( nullptr, bodypart_id( "torso" ), bash_dmg );
5072 critter.check_dead_state();
5073 }
5074 if( !critter.is_dead() && critter.type->size >= MS_HUGE ) {
5075 // big critters simply prevent the gate from closing
5076 // TODO: perhaps damage/destroy the gate
5077 // if the critter was really big?
5078 return false;
5079 }
5080 if( !critter.is_dead() ) {
5081 // Still alive? Move the critter away so the door can close
5082 if( cannot_push ) {
5083 return false;
5084 }
5085 // TODO implement who was closing the door and replace nullptr
5086 knockback( kbp, p, std::max( 1, bash_dmg / 10 ), -1, 1, nullptr );
5087 if( critter_at( p ) ) {
5088 return false;
5089 }
5090 }
5091 }
5092 if( const optional_vpart_position vp = m.veh_at( p ) ) {
5093 if( bash_dmg <= 0 ) {
5094 return false;
5095 }
5096 vp->vehicle().damage( vp->part_index(), bash_dmg );
5097 if( m.veh_at( p ) ) {
5098 // Check again in case all parts at the door tile
5099 // have been destroyed, if there is still a vehicle
5100 // there, the door can not be closed
5101 return false;
5102 }
5103 }
5104 if( bash_dmg < 0 && !m.i_at( p ).empty() ) {
5105 return false;
5106 }
5107 if( bash_dmg == 0 ) {
5108 for( auto &elem : m.i_at( p ) ) {
5109 if( elem.made_of( LIQUID ) ) {
5110 // Liquids are OK, will be destroyed later
5111 continue;
5112 } else if( elem.volume() < 250_ml ) {
5113 // Dito for small items, will be moved away
5114 continue;
5115 }
5116 // Everything else prevents the door from closing
5117 return false;
5118 }
5119 }
5120
5121 m.ter_set( p, door_type );
5122 if( m.has_flag( "NOITEM", p ) ) {
5123 map_stack items = m.i_at( p );
5124 for( map_stack::iterator it = items.begin(); it != items.end(); ) {
5125 if( it->made_of( LIQUID ) ) {
5126 it = items.erase( it );
5127 continue;
5128 }
5129 if( it->made_of( material_id( "glass" ) ) && one_in( 2 ) ) {
5130 if( can_see ) {
5131 add_msg( m_warning, _( "A %s shatters!" ), it->tname() );
5132 } else {
5133 add_msg( m_warning, _( "Something shatters!" ) );
5134 }
5135 it = items.erase( it );
5136 continue;
5137 }
5138 if( cannot_push ) {
5139 return false;
5140 }
5141 m.add_item_or_charges( kbp, *it );
5142 it = items.erase( it );
5143 }
5144 }
5145 return true;
5146}
int hitall(int dam, int vary, Creature *source)
Harms all body parts for dam, with armor reduction.
Definition: character.cpp:8682
void knockback(const tripoint &s, const tripoint &t, int force, int stun, int dam_mult, Creature *source)
Definition: game.cpp:4254
iterator erase(const_iterator it) override
Definition: map.cpp:154
bool ter_set(const tripoint &p, const ter_id &new_terrain)
Definition: map.cpp:1704
void die_in_explosion(Creature *source)
Definition: monster.cpp:1705
bool is_npc() const override
Definition: player.h:103
bool is_player() const override
Definition: player.h:93
@ MS_SMALL
Definition: creature.h:59
@ MS_HUGE
Definition: creature.h:62
@ LIQUID
Definition: enums.h:175
std::optional< tripoint > random_point(const map &m, const std::function< bool(const tripoint &)> &predicate)
Same as other random_point with a range enclosing all valid points of the map.
std::string name() const
Definition: mapdata.cpp:514
m_size size
Definition: mtype.h:262

References _, Character::activity, map::add_item_or_charges(), add_msg(), monster::apply_damage(), item_stack::begin(), Character::cancel_activity(), Creature::check_dead_state(), critter_at(), monster::die_in_explosion(), item_stack::empty(), item_stack::end(), map_stack::erase(), g, map::has_flag(), Character::hitall(), map::i_at(), monster::is_dead(), player::is_npc(), player::is_player(), knockback(), LIQUID, m, m_bad, m_warning, MS_HUGE, MS_SMALL, Character::name, map_data_common_t::name(), monster::name(), int_id< T >::obj(), one_in(), map::points_in_radius(), random_point(), Character::sees(), mtype::size, map::ter_set(), monster::type, u, and map::veh_at().

◆ gametype()

special_game_type game::gametype ( ) const

Definition at line 539 of file game.cpp.

540{
542}

References gamemode, and NONE.

◆ get_creature_if()

Creature * game::get_creature_if ( const std::function< bool(const Creature &)> &  pred)

Returns a creature matching a predicate.

Only living (not dead) creatures are checked. Returns nullptr if no creature matches the predicate. There is no guarantee which creature is returned when several creatures match.

Definition at line 12052 of file game.cpp.

12053{
12054 for( Creature &critter : all_creatures() ) {
12055 if( pred( critter ) ) {
12056 return &critter;
12057 }
12058 }
12059 return nullptr;
12060}

References all_creatures().

◆ get_creatures_if()

std::vector< Creature * > game::get_creatures_if ( const std::function< bool(const Creature &)> &  pred)

Returns all creatures matching a predicate.

Only living ( not dead ) creatures are checked ( and returned ). Returned pointers are never null.

Definition at line 11962 of file game.cpp.

11964{
11965 std::vector<Creature *> result;
11966 for( Creature &critter : all_creatures() ) {
11967 if( pred( critter ) ) {
11968 result.push_back( &critter );
11969 }
11970 }
11971 return result;
11972}

References all_creatures().

◆ get_cur_om()

overmap & game::get_cur_om ( ) const

The overmap which contains the center submap of the reality bubble.

Definition at line 11942 of file game.cpp.

11943{
11944 // The player is located in the middle submap of the map.
11946 const tripoint pos_om = sm_to_om_copy( sm );
11947 // TODO: fix point types
11948 return overmap_buffer.get( point_abs_om( pos_om.xy() ) );
11949}
tripoint get_abs_sub() const
return abs_sub
Definition: map.cpp:8433
overmap & get(const point_abs_om &)
Uses overmap coordinates, that means x and y are directly compared with the position of the overmap.
point sm_to_om_copy(point p)
coords::coord_point< point, coords::origin::abs, coords::om > point_abs_om
Definition: coordinates.h:483
static constexpr int HALF_MAPSIZE
constexpr scale sm
Definition: coordinates.h:31

References overmapbuffer::get(), map::get_abs_sub(), HALF_MAPSIZE, m, overmap_buffer, coords::sm, sm_to_om_copy(), and tripoint::xy().

Referenced by start_game().

◆ get_dangerous_tile()

std::vector< std::string > game::get_dangerous_tile ( const tripoint dest_loc) const

Definition at line 8748 of file game.cpp.

8749{
8750 std::vector<std::string> harmful_stuff;
8751 const auto fields_here = m.field_at( u.pos() );
8752 for( const auto &e : m.field_at( dest_loc ) ) {
8753 // warn before moving into a dangerous field except when already standing within a similar field
8754 if( u.is_dangerous_field( e.second ) && fields_here.find_field( e.first ) == nullptr ) {
8755 harmful_stuff.push_back( e.second.name() );
8756 }
8757 }
8758
8759 if( !u.is_blind() ) {
8760 const trap &tr = m.tr_at( dest_loc );
8761 const bool boardable = static_cast<bool>( m.veh_at( dest_loc ).part_with_feature( "BOARDABLE",
8762 true ) );
8763 // HACK: Hack for now, later ledge should stop being a trap
8764 // Note: in non-z-level mode, ledges obey different rules and so should be handled as regular traps
8765 if( tr.loadid == tr_ledge && m.has_zlevels() ) {
8766 if( !boardable ) {
8767 harmful_stuff.emplace_back( tr.name() );
8768 }
8769 } else if( tr.can_see( dest_loc, u ) && !tr.is_benign() && !boardable ) {
8770 harmful_stuff.emplace_back( tr.name() );
8771 }
8772
8773 static const std::set< body_part > sharp_bps = {
8776 };
8777
8778 const auto sharp_bp_check = [this]( body_part bp ) {
8779 return character_funcs::is_bp_immune_to( u, bp, { DT_CUT, 10 } );
8780 };
8781
8782 if( m.has_flag( "ROUGH", dest_loc ) && !m.has_flag( "ROUGH", u.pos() ) && !boardable &&
8783 ( u.get_armor_bash( bodypart_id( "foot_l" ) ) < 5 ||
8784 u.get_armor_bash( bodypart_id( "foot_r" ) ) < 5 ) ) {
8785 harmful_stuff.emplace_back( m.name( dest_loc ) );
8786 } else if( m.has_flag( "SHARP", dest_loc ) && !m.has_flag( "SHARP", u.pos() ) && !( u.in_vehicle ||
8787 m.veh_at( dest_loc ) ) &&
8788 u.dex_cur < 78 && !std::all_of( sharp_bps.begin(), sharp_bps.end(), sharp_bp_check ) ) {
8789 harmful_stuff.emplace_back( m.name( dest_loc ) );
8790 }
8791
8792 }
8793
8794 return harmful_stuff;
8795}
@ bp_foot_l
Definition: bodypart.h:52
@ bp_leg_r
Definition: bodypart.h:51
@ bp_eyes
Definition: bodypart.h:44
@ bp_hand_l
Definition: bodypart.h:48
@ bp_arm_l
Definition: bodypart.h:46
@ bp_leg_l
Definition: bodypart.h:50
@ bp_hand_r
Definition: bodypart.h:49
@ bp_head
Definition: bodypart.h:43
@ bp_torso
Definition: bodypart.h:42
@ bp_mouth
Definition: bodypart.h:45
@ bp_foot_r
Definition: bodypart.h:53
@ bp_arm_r
Definition: bodypart.h:47
int dex_cur
Definition: character.h:265
int get_armor_bash(bodypart_id bp) const override
Returns overall bashing resistance for the body_part.
Definition: character.cpp:6864
bool is_dangerous_field(const field_entry &entry) const
Returns true if the given field entry is dangerous to us.
Definition: creature.cpp:199
const field & field_at(const tripoint &p) const
Get the fields that are here.
Definition: map.cpp:5420
bool has_zlevels() const
Definition: map.h:1640
@ DT_CUT
Definition: damage.h:25
bool is_bp_immune_to(const Character &who, body_part bp, damage_unit dam)
Check if character's body part is immune to given damage.
Definition: trap.h:86
std::string name() const
Definition: trap.cpp:177
bool can_see(const tripoint &pos, const Character &p) const
Can player/npc p see this kind of trap, either by their memory (they known there is the trap) or by t...
Definition: trap.cpp:223
bool is_benign() const
If true, this is not really a trap and there won't be any safety queries before stepping onto it (e....
Definition: trap.h:159

References bp_arm_l, bp_arm_r, bp_eyes, bp_foot_l, bp_foot_r, bp_hand_l, bp_hand_r, bp_head, bp_leg_l, bp_leg_r, bp_mouth, bp_torso, trap::can_see(), Character::dex_cur, DT_CUT, map::field_at(), Character::get_armor_bash(), map::has_flag(), map::has_zlevels(), Character::in_vehicle, trap::is_benign(), Character::is_blind(), character_funcs::is_bp_immune_to(), Creature::is_dangerous_field(), trap::loadid, m, trap::name(), map::name(), optional_vpart_position::part_with_feature(), Character::pos(), map::tr_at(), tr_ledge, u, and map::veh_at().

Referenced by is_dangerous_tile(), prompt_dangerous_tile(), and walk_move().

◆ get_fishable_locations()

std::unordered_set< tripoint > game::get_fishable_locations ( int  distance,
const tripoint fish_pos 
)

Get the contiguous fishable locations starting at fish_pos, out to the specificed distance.

Parameters
distanceDistance around the fish_pos to examine for contiguous fishable locations.
fish_posThe location being fished.
Returns
A set of locations representing the valid contiguous fishable locations.

Definition at line 3612 of file game.cpp.

3613{
3614 // We're going to get the contiguous fishable terrain starting at
3615 // the provided fishing location (e.g. where a line was cast or a fish
3616 // trap was set), and then check whether or not fishable monsters are
3617 // actually in those locations. This will help us ensure that we're
3618 // getting our fish from the location that we're ACTUALLY fishing,
3619 // rather than just somewhere in the vicinity.
3620
3621 std::unordered_set<tripoint> visited;
3622
3623 const tripoint fishing_boundary_min( fish_pos + point( -distance, -distance ) );
3624 const tripoint fishing_boundary_max( fish_pos + point( distance, distance ) );
3625
3626 const inclusive_cuboid<tripoint> fishing_boundaries(
3627 fishing_boundary_min, fishing_boundary_max );
3628
3629 const auto get_fishable_terrain = [&]( tripoint starting_point,
3630 std::unordered_set<tripoint> &fishable_terrain ) {
3631 std::queue<tripoint> to_check;
3632 to_check.push( starting_point );
3633 while( !to_check.empty() ) {
3634 const tripoint current_point = to_check.front();
3635 to_check.pop();
3636
3637 // We've been here before, so bail.
3638 if( visited.find( current_point ) != visited.end() ) {
3639 continue;
3640 }
3641
3642 // This point is out of bounds, so bail.
3643 if( !fishing_boundaries.contains( current_point ) ) {
3644 continue;
3645 }
3646
3647 // Mark this point as visited.
3648 visited.emplace( current_point );
3649
3650 if( m.has_flag( "FISHABLE", current_point ) ) {
3651 fishable_terrain.emplace( current_point );
3652 to_check.push( current_point + point_south );
3653 to_check.push( current_point + point_north );
3654 to_check.push( current_point + point_east );
3655 to_check.push( current_point + point_west );
3656 }
3657 }
3658 return;
3659 };
3660
3661 // Starting at the provided location, get our fishable terrain
3662 // and populate a set with those locations which we'll then use
3663 // to determine if any fishable monsters are in those locations.
3664 std::unordered_set<tripoint> fishable_points;
3665 get_fishable_terrain( fish_pos, fishable_points );
3666
3667 return fishable_points;
3668}
static constexpr point point_west
Definition: point.h:268
static constexpr point point_south
Definition: point.h:266
static constexpr point point_north
Definition: point.h:262
static constexpr point point_east
Definition: point.h:264

References inclusive_cuboid< Tripoint, >::contains(), map::has_flag(), m, point_east, point_north, point_south, and point_west.

◆ get_fishable_monsters()

std::vector< monster * > game::get_fishable_monsters ( std::unordered_set< tripoint > &  fishable_locations)

Get the fishable monsters within the provided fishable locations.

Parameters
fishable_locationsA set of locations which are valid fishable terrain. Any fishable monsters are filtered by this collection to determine those which can actually be caught.
Returns
Fishable monsters within the specified fishable terrain.

Definition at line 3670 of file game.cpp.

3672{
3673 std::vector<monster *> unique_fish;
3674 for( monster &critter : all_monsters() ) {
3675 // If it is fishable...
3676 if( critter.has_flag( MF_FISHABLE ) ) {
3677 const tripoint critter_pos = critter.pos();
3678 // ...and it is in a fishable location.
3679 if( fishable_locations.find( critter_pos ) != fishable_locations.end() ) {
3680 unique_fish.push_back( &critter );
3681 }
3682 }
3683 }
3684
3685 return unique_fish;
3686}
@ MF_FISHABLE
Definition: mtype.h:142

References all_monsters(), and MF_FISHABLE.

◆ get_follower_list()

std::set< character_id > game::get_follower_list ( )

Get set of followers.

Definition at line 1967 of file game.cpp.

1968{
1969 return follower_ids;
1970}

References follower_ids.

◆ get_kill_tracker()

kill_tracker & game::get_kill_tracker ( )

Definition at line 2724 of file game.cpp.

2725{
2726 return *kill_tracker_ptr;
2727}

References kill_tracker_ptr.

Referenced by cleanup_at_end(), death_screen(), handle_action(), setup(), and win().

◆ get_levx()

int game::get_levx ( ) const

The top left corner of the reality bubble (in submaps coordinates).

This is the same as map::abs_sub of the m map.

Definition at line 11927 of file game.cpp.

11928{
11929 return m.get_abs_sub().x;
11930}

References map::get_abs_sub(), m, and tripoint::x.

Referenced by create_starting_npcs(), load_npcs(), look_around(), save_cyborg(), spawn_hallucination(), vertical_move(), and vertical_shift().

◆ get_levy()

int game::get_levy ( ) const

Definition at line 11932 of file game.cpp.

11933{
11934 return m.get_abs_sub().y;
11935}

References map::get_abs_sub(), m, and tripoint::y.

Referenced by create_starting_npcs(), load_npcs(), look_around(), save_cyborg(), spawn_hallucination(), vertical_move(), and vertical_shift().

◆ get_levz()

◆ get_moves_since_last_save()

int game::get_moves_since_last_save ( ) const

Definition at line 7128 of file game.cpp.

7129{
7130 return moves_since_last_save;
7131}

References moves_since_last_save.

◆ get_npcs_if()

std::vector< npc * > game::get_npcs_if ( const std::function< bool(const npc &)> &  pred)

Definition at line 11974 of file game.cpp.

11975{
11976 std::vector<npc *> result;
11977 for( npc &guy : all_npcs() ) {
11978 if( pred( guy ) ) {
11979 result.push_back( &guy );
11980 }
11981 }
11982 return result;
11983}

References all_npcs().

Referenced by allies(), chat(), and validate_npc_followers().

◆ get_player_base_save_path()

std::string game::get_player_base_save_path ( ) const

Base path for saving player data.

Just add a suffix (unique for the thing you want to save) and use the resulting path. Example: save_ui_data(get_player_base_save_path()+".ui")

Definition at line 12062 of file game.cpp.

12063{
12064 return get_world_base_save_path() + "/" + base64_encode( get_avatar().get_save_id() );
12065}
std::string base64_encode(const std::string &str)
std::string get_world_base_save_path() const
Base path for saving world data.
Definition: game.cpp:12067
friend avatar & get_avatar()
Definition: avatar.cpp:105

References base64_encode(), get_avatar, and get_world_base_save_path().

Referenced by save_player_data().

◆ get_player_input()

input_context game::get_player_input ( std::string &  action)
private

Definition at line 247 of file handle_action.cpp.

248{
249 input_context ctxt;
250 if( uquit == QUIT_WATCH ) {
251 ctxt = input_context( "DEFAULTMODE" );
252 ctxt.set_iso( true );
253 // The list of allowed actions in death-cam mode in game::handle_action
254 // *INDENT-OFF*
255 for( const action_id id : {
268 } ) {
269 ctxt.register_action( action_ident( id ) );
270 }
271 // *INDENT-ON*
272 ctxt.register_action( "QUIT", to_translation( "Accept your fate" ) );
273 } else {
275 }
276
278
279 user_turn current_turn;
280
281
282 // Checking early if we will need to handle animations
283 // If we do not need to handle animations that will not change as long as the user has not selected an action
284 // and we can handle it like we are not animating.
285 weather_printable wPrint;
286 bool animate_weather = false;
287 bool animate_sct = false;
288 bool do_animations = [&]() {
289 if( get_option<bool>( "ANIMATIONS" ) ) {
290 const bool weather_has_anim = init_weather_anim( get_weather().weather_id, wPrint );
291
292 animate_weather = weather_has_anim && get_option<bool>( "ANIMATION_RAIN" );
293 animate_sct = !SCT.vSCT.empty() && uquit != QUIT_WATCH && get_option<bool>( "ANIMATION_SCT" );
294
295#if defined(TILES)
296 // Always animate, minimap and terrain may have animations to run
297 return true;
298#else
299 // Otherwise we need to see if we actually should animate.
300 // Minimap and Terrain never animate in !TILES
301 return animate_weather || animate_sct || uquit == QUIT_WATCH;
302#endif
303 }
304 return false;
305 }
306 ();
307
308 if( do_animations ) {
309 ctxt.set_timeout( 125 );
310
312 make_shared_fast<game::draw_callback_t>( [&]() {
313 if( animate_weather ) {
314 draw_weather( wPrint );
315 }
316 if( animate_sct ) {
317 draw_sct();
318 }
319 } );
320 add_draw_callback( animation_cb );
321 invalidate_main_ui_adaptor(); // We want to redraw at least once.
322
323 do {
324 if( animate_weather ) {
326 generate_weather_anim_frame( get_weather().weather_id, wPrint );
327 }
328 // don't bother calculating SCT if we won't show it
329 if( animate_sct ) {
331
333
334 //Check for creatures on all drawing positions and offset if necessary
335 for( auto iter = SCT.vSCT.rbegin(); iter != SCT.vSCT.rend(); ++iter ) {
336 const direction oCurDir = iter->getDirecton();
337 const int width = utf8_width( iter->getText() );
338 for( int i = 0; i < width; ++i ) {
339 tripoint tmp( iter->getPosX() + i, iter->getPosY(), get_levz() );
340 const Creature *critter = critter_at( tmp, true );
341
342 if( critter != nullptr && u.sees( *critter ) ) {
343 i = -1;
344 int iPos = iter->getStep() + iter->getStepOffset();
345 for( auto iter2 = iter; iter2 != SCT.vSCT.rend(); ++iter2 ) {
346 if( iter2->getDirecton() == oCurDir &&
347 iter2->getStep() + iter2->getStepOffset() <= iPos ) {
348 if( iter2->getType() == "hp" ) {
349 iter2->advanceStepOffset();
350 }
351
352 iter2->advanceStepOffset();
353 iPos = iter2->getStep() + iter2->getStepOffset();
354 }
355 }
356 }
357 }
358 }
359
360 // Stop animation when done
361 animate_sct = !SCT.vSCT.empty();
362 }
363 // We don't cache these checks as their result may change after 1st redraw
365 // TODO: we redraw *everything* just to animate a couple blinking dots
366 // on the minimap or a few tiles.
367 // This is far from ideal, and can probably be done much cheaper
368 // (update only part of the screen? draw static parts into a texture?)
370 }
371
372 std::unique_ptr<static_popup> deathcam_msg_popup;
373 if( uquit == QUIT_WATCH ) {
374 deathcam_msg_popup = std::make_unique<static_popup>();
375 deathcam_msg_popup
376 ->wait_message( c_red, _( "Press %s to accept your fate…" ), ctxt.get_desc( "QUIT" ) )
377 .on_top( true );
378 }
379
381 } while( handle_mouseview( ctxt, action ) && uquit != QUIT_WATCH
382 && ( action != "TIMEOUT" || !current_turn.has_timeout_elapsed() ) );
383 ctxt.reset_timeout();
384 } else {
387 SCT.vSCT.clear();
388
389 ctxt.set_timeout( 125 );
390 while( handle_mouseview( ctxt, action ) ) {
391 if( action == "TIMEOUT" && current_turn.has_timeout_elapsed() ) {
392 break;
393 }
394 }
395 ctxt.reset_timeout();
396 }
397
398 return ctxt;
399}
std::string action_ident(action_id act)
Lookup a unique string identifier for a given action ID.
Definition: action.cpp:70
action_id
Enumerates all discrete actions that can be performed by player.
Definition: action.h:18
@ ACTION_CENTER
Center the viewport on character.
Definition: action.h:73
@ ACTION_SHIFT_SW
Move viewport south-west.
Definition: action.h:85
@ ACTION_SHIFT_NW
Move viewport north-west.
Definition: action.h:89
@ ACTION_KEYBINDINGS
Display keybindings list.
Definition: action.h:255
@ ACTION_SHIFT_E
Move viewport east.
Definition: action.h:79
@ ACTION_TOGGLE_MAP_MEMORY
Toggle memorized tiles being shown.
Definition: action.h:71
@ ACTION_SHIFT_S
Move viewport south.
Definition: action.h:83
@ ACTION_SHIFT_SE
Move viewport south-east.
Definition: action.h:81
@ ACTION_LOOK
Toggle look mode.
Definition: action.h:115
@ ACTION_SHIFT_NE
Move viewport north-east.
Definition: action.h:77
@ ACTION_SHIFT_W
Move viewport west.
Definition: action.h:87
@ ACTION_SHIFT_N
Move viewport north.
Definition: action.h:75
bool terrain_requires_animation()
Definition: animation.cpp:1204
bool minimap_requires_animation()
Definition: animation.cpp:1195
void draw_sct()
Definition: animation.cpp:865
void draw_weather(const weather_printable &wPrint)
Definition: animation.cpp:824
void add_draw_callback(shared_ptr_fast< draw_callback_t > cb)
Definition: game.cpp:3025
bool handle_mouseview(input_context &ctxt, std::string &action)
Definition: game.cpp:1998
void set_timeout(int val)
Sets input polling timeout as appropriate for the current interface system.
Definition: input.cpp:1452
std::string get_desc(const std::string &action_descriptor, unsigned int max_limit=0, const input_event_filter &evt_filter=allow_all_keys) const
Get a description text for the key/other input method associated with the given action.
Definition: input.cpp:750
void register_action(const std::string &action_descriptor)
Register an action with this input context.
Definition: input.cpp:672
void set_iso(bool mode=true)
Definition: input.cpp:1423
void reset_timeout()
Definition: input.cpp:1457
std::vector< cSCT > vSCT
Definition: output.h:916
void advanceAllSteps()
Definition: output.cpp:1924
bool has_timeout_elapsed()
input_context get_default_mode_input_context()
Definition: game.cpp:2098
static bool init_weather_anim(const weather_type_id &wtype, weather_printable &wPrint)
static void generate_weather_anim_frame(const weather_type_id &wtype, weather_printable &wPrint)
direction
Definition: line.h:39
scrollingcombattext SCT
Definition: output.cpp:65
Weather drawing tracking.
Definition: weather.h:59
translation to_translation(const std::string &raw)
Shorthands for translation::to_translation.

References _, action, ACTION_CENTER, action_ident(), ACTION_KEYBINDINGS, ACTION_LOOK, ACTION_SHIFT_E, ACTION_SHIFT_N, ACTION_SHIFT_NE, ACTION_SHIFT_NW, ACTION_SHIFT_S, ACTION_SHIFT_SE, ACTION_SHIFT_SW, ACTION_SHIFT_W, ACTION_TOGGLE_MAP_MEMORY, add_draw_callback(), scrollingcombattext::advanceAllSteps(), c_red, critter_at(), draw_sct(), draw_weather(), generate_weather_anim_frame(), get_default_mode_input_context(), input_context::get_desc(), get_levz(), get_weather, handle_mouseview(), user_turn::has_timeout_elapsed(), init_weather_anim(), invalidate_main_ui_adaptor(), m, minimap_requires_animation(), Character::posz(), QUIT_WATCH, ui_manager::redraw_invalidated(), input_context::register_action(), input_context::reset_timeout(), SCT, Character::sees(), input_context::set_iso(), input_context::set_timeout(), terrain_requires_animation(), to_translation(), u, map::update_visibility_cache(), uquit, utf8_width(), and scrollingcombattext::vSCT.

Referenced by handle_action().

◆ get_seed()

unsigned int game::get_seed ( ) const

Definition at line 1779 of file game.cpp.

1780{
1781 return seed;
1782}

References seed.

◆ get_user_action_counter()

int game::get_user_action_counter ( ) const

Definition at line 7133 of file game.cpp.

7134{
7135 return user_action_counter;
7136}

References user_action_counter.

◆ get_veh_dir_indicator_location()

std::optional< tripoint > game::get_veh_dir_indicator_location ( bool  next) const

Returns the location where the indicator should go relative to the reality bubble, or nothing to indicate no indicator should be drawn.

Based on the vehicle the player is driving, if any.

Parameters
nextIf true, bases it on the vehicle the vehicle will turn to next turn, instead of the one it is currently facing.

Definition at line 3280 of file game.cpp.

3281{
3282 if( !get_option<bool>( "VEHICLE_DIR_INDICATOR" ) ) {
3283 return std::nullopt;
3284 }
3285 const optional_vpart_position vp = m.veh_at( u.pos() );
3286 if( !vp ) {
3287 return std::nullopt;
3288 }
3289 vehicle *const veh = &vp->vehicle();
3290 rl_vec2d face = next ? veh->dir_vec() : veh->face_vec();
3291 float r = 10.0;
3292 return tripoint( static_cast<int>( r * face.x ), static_cast<int>( r * face.y ), u.pos().z );
3293}
rl_vec2d dir_vec() const

References vehicle::dir_vec(), vehicle::face_vec(), m, Character::pos(), u, map::veh_at(), rl_vec2d::x, rl_vec2d::y, and tripoint::z.

Referenced by draw_veh_dir_indicator().

◆ get_world_base_save_path()

std::string game::get_world_base_save_path ( ) const

Base path for saving world data.

This yields a path to a folder.

Definition at line 12067 of file game.cpp.

12068{
12069 if( world_generator->active_world == nullptr ) {
12070 return PATH_INFO::savedir();
12071 }
12072 return world_generator->active_world->folder_path();
12073}
std::string savedir()
Definition: path_info.cpp:246

References PATH_INFO::savedir(), and world_generator.

Referenced by get_player_base_save_path(), load(), load_master(), move_save_to_graveyard(), save_artifacts(), save_factions_missions_npcs(), and setup().

◆ get_zoom()

int game::get_zoom ( ) const

Definition at line 7119 of file game.cpp.

7120{
7121#if defined(TILES)
7122 return tileset_zoom;
7123#else
7124 return DEFAULT_TILESET_ZOOM;
7125#endif
7126}

References DEFAULT_TILESET_ZOOM, and tileset_zoom.

Referenced by look_around().

◆ grabbed_furn_move()

bool game::grabbed_furn_move ( const tripoint dp)
private
Strength determines ability to drag furniture

Definition at line 9553 of file game.cpp.

9554{
9555 // Furniture: pull, push, or standing still and nudging object around.
9556 // Can push furniture out of reach.
9557 tripoint fpos = u.pos() + u.grab_point;
9558 // supposed position of grabbed furniture
9559 if( !m.has_furn( fpos ) ) {
9560 // Where did it go? We're grabbing thin air so reset.
9561 add_msg( m_info, _( "No furniture at grabbed point." ) );
9562 u.grab( OBJECT_NONE );
9563 return false;
9564 }
9565
9566 const bool pushing_furniture = dp == u.grab_point;
9567 const bool pulling_furniture = dp == -u.grab_point;
9568 const bool shifting_furniture = !pushing_furniture && !pulling_furniture;
9569
9570 tripoint fdest = fpos + dp; // intended destination of furniture.
9571 // Check floor: floorless tiles don't need to be flat and have no traps
9572 const bool has_floor = m.has_floor( fdest );
9573 // Unfortunately, game::is_empty fails for tiles we're standing on,
9574 // which will forbid pulling, so:
9575 const bool canmove = (
9576 m.passable( fdest ) &&
9577 critter_at<npc>( fdest ) == nullptr &&
9578 critter_at<monster>( fdest ) == nullptr &&
9579 ( !pulling_furniture || is_empty( u.pos() + dp ) ) &&
9580 ( !has_floor || m.has_flag( "FLAT", fdest ) ) &&
9581 !m.has_furn( fdest ) &&
9582 !m.veh_at( fdest ) &&
9583 ( !has_floor || m.tr_at( fdest ).is_null() )
9584 );
9585
9586 const furn_t furntype = m.furn( fpos ).obj();
9587 const int src_items = m.i_at( fpos ).size();
9588 const int dst_items = m.i_at( fdest ).size();
9589
9590 const bool only_liquid_items = std::all_of( m.i_at( fdest ).begin(), m.i_at( fdest ).end(),
9591 [&]( item & liquid_item ) {
9592 return liquid_item.made_of( LIQUID );
9593 } );
9594
9595 const bool dst_item_ok = !m.has_flag( "NOITEM", fdest ) &&
9596 !m.has_flag( "SWIMMABLE", fdest ) &&
9597 !m.has_flag( "DESTROY_ITEM", fdest );
9598
9599 const bool src_item_ok = m.furn( fpos ).obj().has_flag( "CONTAINER" ) ||
9600 m.furn( fpos ).obj().has_flag( "FIRE_CONTAINER" ) ||
9601 m.furn( fpos ).obj().has_flag( "SEALED" );
9602
9603 const int fire_intensity = m.get_field_intensity( fpos, fd_fire );
9604 time_duration fire_age = m.get_field_age( fpos, fd_fire );
9605
9606 int str_req = furntype.move_str_req;
9607 // Factor in weight of items contained in the furniture.
9608 units::mass furniture_contents_weight = 0_gram;
9609 for( auto &contained_item : m.i_at( fpos ) ) {
9610 furniture_contents_weight += contained_item.weight();
9611 }
9612 str_req += furniture_contents_weight / 4_kilogram;
9613 int adjusted_str = u.get_str();
9614 if( u.is_mounted() ) {
9615 auto mons = u.mounted_creature.get();
9616 if( mons->has_flag( MF_RIDEABLE_MECH ) && mons->mech_str_addition() != 0 ) {
9617 adjusted_str = mons->mech_str_addition();
9618 }
9619 }
9620 if( !canmove ) {
9621 // TODO: What is something?
9622 add_msg( _( "The %s collides with something." ), furntype.name() );
9623 u.moves -= 50;
9624 return true;
9625 ///\EFFECT_STR determines ability to drag furniture
9626 } else if( str_req > adjusted_str &&
9627 one_in( std::max( 20 - str_req - adjusted_str, 2 ) ) ) {
9628 add_msg( m_bad, _( "You strain yourself trying to move the heavy %s!" ),
9629 furntype.name() );
9630 u.moves -= 100;
9631 u.mod_pain( 1 ); // Hurt ourselves.
9632 return true; // furniture and or obstacle wins.
9633 } else if( !src_item_ok && !only_liquid_items && dst_items > 0 ) {
9634 add_msg( _( "There's stuff in the way." ) );
9635 u.moves -= 50;
9636 return true;
9637 }
9638
9639 u.moves -= str_req * 10;
9640 // Additional penalty if we can't comfortably move it.
9641 if( str_req > adjusted_str ) {
9642 int move_penalty = std::pow( str_req, 2.0 ) + 100.0;
9643 if( move_penalty <= 1000 ) {
9644 if( adjusted_str >= str_req - 3 ) {
9645 u.moves -= std::max( 3000, move_penalty * 10 );
9646 add_msg( m_bad, _( "The %s is really heavy!" ), furntype.name() );
9647 if( one_in( 3 ) ) {
9648 add_msg( m_bad, _( "You fail to move the %s." ), furntype.name() );
9649 return true;
9650 }
9651 } else {
9652 u.moves -= 100;
9653 add_msg( m_bad, _( "The %s is too heavy for you to budge." ), furntype.name() );
9654 return true;
9655 }
9656 }
9657 u.moves -= move_penalty;
9658 if( move_penalty > 500 ) {
9659 add_msg( _( "Moving the heavy %s is taking a lot of time!" ),
9660 furntype.name() );
9661 } else if( move_penalty > 200 ) {
9662 if( one_in( 3 ) ) { // Nag only occasionally.
9663 add_msg( _( "It takes some time to move the heavy %s." ),
9664 furntype.name() );
9665 }
9666 }
9667 }
9669 _( "a scraping noise." ), true, "misc", "scraping" );
9670
9672 ( tripoint_abs_ms( m.getabs( fpos ) ) );
9673
9674 // Actually move the furniture.
9675 m.furn_set( fdest, m.furn( fpos ), atd ? atd->clone() : nullptr );
9676 m.furn_set( fpos, f_null );
9677
9678 if( fire_intensity == 1 && !pulling_furniture ) {
9679 m.remove_field( fpos, fd_fire );
9680 m.set_field_intensity( fdest, fd_fire, fire_intensity );
9681 m.set_field_age( fdest, fd_fire, fire_age );
9682 }
9683
9684 // Is there is only liquids on the ground, remove them after moving furniture.
9685 if( dst_items > 0 && only_liquid_items ) {
9686 m.i_clear( fdest );
9687 }
9688
9689 if( src_items > 0 ) { // Move the stuff inside.
9690 if( dst_item_ok && src_item_ok ) {
9691 // Assume contents of both cells are legal, so we can just swap contents.
9692 std::list<item> temp;
9693 std::move( m.i_at( fpos ).begin(), m.i_at( fpos ).end(),
9694 std::back_inserter( temp ) );
9695 m.i_clear( fpos );
9696 for( auto item_iter = m.i_at( fdest ).begin();
9697 item_iter != m.i_at( fdest ).end(); ++item_iter ) {
9698 m.i_at( fpos ).insert( *item_iter );
9699 }
9700 m.i_clear( fdest );
9701 for( auto &cur_item : temp ) {
9702 m.i_at( fdest ).insert( cur_item );
9703 }
9704 } else {
9705 add_msg( _( "Stuff spills from the %s!" ), furntype.name() );
9706 }
9707 }
9708
9709 if( shifting_furniture ) {
9710 // We didn't move
9711 tripoint d_sum = u.grab_point + dp;
9712 if( std::abs( d_sum.x ) < 2 && std::abs( d_sum.y ) < 2 ) {
9713 u.grab_point = d_sum; // furniture moved relative to us
9714 } else { // we pushed furniture out of reach
9715 add_msg( _( "You let go of the %s." ), furntype.name() );
9716 u.grab( OBJECT_NONE );
9717 }
9718 return true; // We moved furniture but stayed still.
9719 }
9720
9721 if( pushing_furniture && m.impassable( fpos ) ) {
9722 // Not sure how that chair got into a wall, but don't let player follow.
9723 add_msg( _( "You let go of the %1$s as it slides past %2$s." ),
9724 furntype.name(), m.tername( fdest ) );
9725 u.grab( OBJECT_NONE );
9726 return true;
9727 }
9728
9729 return false;
9730}
virtual int get_str() const
Getters for stats exclusive to characters.
Definition: character.cpp:4089
virtual active_tile_data * clone() const =0
void grab(object_type grab_type, const tripoint &grab_point=tripoint_zero)
Definition: avatar.cpp:665
bool is_empty(const tripoint &p)
Returns true if there is no player, NPC, or monster on the tile and move_cost > 0.
Definition: game.cpp:4849
void insert(const item &newitem) override
Definition: map.cpp:159
void remove_field(const tripoint &p, const field_type_id &field_to_remove)
Remove field entry at xy, ignored if the field entry is not present.
Definition: map.cpp:5593
time_duration set_field_age(const tripoint &p, const field_type_id &type, const time_duration &age, bool isoffset=false)
Set age of field entry at point.
Definition: map.cpp:5460
time_duration get_field_age(const tripoint &p, const field_type_id &type) const
Get the age of a field entry (field_entry::age), if there is no field of that type,...
Definition: map.cpp:5494
int get_field_intensity(const tripoint &p, const field_type_id &type) const
Get the intensity of a field entry (field_entry::intensity), if there is no field of that type,...
Definition: map.cpp:5500
int set_field_intensity(const tripoint &p, const field_type_id &type, int new_intensity, bool isoffset=false)
Set intensity of field entry at point, creating if not present, removing if intensity becomes 0.
Definition: map.cpp:5473
std::string tername(const tripoint &p) const
Definition: map.cpp:1774
void i_clear(const tripoint &p)
Definition: map.cpp:4248
void furn_set(const tripoint &p, const furn_id &new_furniture, cata::poly_serialized< active_tile_data > new_active=nullptr)
Sets the furniture at given position.
Definition: map.cpp:1425
bool has_floor(const tripoint &p) const
Definition: map.cpp:2072
tripoint grab_point
Definition: player.h:235
@ OBJECT_NONE
Definition: enums.h:187
field_type_id fd_fire
Definition: field_type.cpp:345
furn_id f_null
Definition: mapdata.cpp:1098
template active_tile_data * furn_at< active_tile_data >(const tripoint_abs_ms &)
bool move(avatar &you, map &m, const tripoint &d)
void sound(const tripoint &p, int vol, sound_t category, const std::string &description, bool ambient=false, const std::string &id="", const std::string &variant="default")
Sound at (p) of intensity (vol)
Definition: sounds.cpp:178
int move_str_req
Definition: mapdata.h:519
bool has_flag(const std::string &flag) const
Definition: mapdata.h:421

References _, add_msg(), item_stack::begin(), active_tile_data::clone(), item_stack::end(), f_null, fd_fire, map::furn(), active_tiles::furn_at< active_tile_data >(), map::furn_set(), map::get_field_age(), map::get_field_intensity(), Character::get_str(), map::getabs(), avatar::grab(), player::grab_point, map_data_common_t::has_flag(), map::has_flag(), map::has_floor(), map::has_furn(), map::i_at(), map::i_clear(), map::impassable(), map_stack::insert(), is_empty(), Character::is_mounted(), trap::is_null(), m, m_bad, m_info, MF_RIDEABLE_MECH, Character::mod_pain(), Character::mounted_creature, avatar_action::move(), furn_t::move_str_req, sounds::movement, Creature::moves, map_data_common_t::name(), int_id< T >::obj(), OBJECT_NONE, one_in(), map::passable(), Character::pos(), map::remove_field(), map::set_field_age(), map::set_field_intensity(), item_stack::size(), sounds::sound(), map::tername(), map::tr_at(), u, map::veh_at(), tripoint::x, and tripoint::y.

Referenced by grabbed_move().

◆ grabbed_move()

bool game::grabbed_move ( const tripoint dp)
private

Check for dangerous stuff at dest_loc, return false if the player decides not to step there.

Definition at line 9732 of file game.cpp.

9733{
9734 if( u.get_grab_type() == OBJECT_NONE ) {
9735 return false;
9736 }
9737
9738 if( dp.z != 0 ) {
9739 // No dragging stuff up/down stairs yet!
9740 return false;
9741 }
9742
9743 // vehicle: pulling, pushing, or moving around the grabbed object.
9744 if( u.get_grab_type() == OBJECT_VEHICLE ) {
9745 return grabbed_veh_move( dp );
9746 }
9747
9748 if( u.get_grab_type() == OBJECT_FURNITURE ) {
9749 return grabbed_furn_move( dp );
9750 }
9751
9752 add_msg( m_info, _( "Nothing at grabbed point %d,%d,%d or bad grabbed object type." ),
9754 u.grab( OBJECT_NONE );
9755 return false;
9756}
object_type get_grab_type() const
Definition: avatar.cpp:673
bool grabbed_furn_move(const tripoint &dp)
Definition: game.cpp:9553
bool grabbed_veh_move(const tripoint &dp)
Definition: grab.cpp:95
@ OBJECT_FURNITURE
Definition: enums.h:197
@ OBJECT_VEHICLE
Definition: enums.h:193

References _, add_msg(), avatar::get_grab_type(), avatar::grab(), player::grab_point, grabbed_furn_move(), grabbed_veh_move(), m_info, OBJECT_FURNITURE, OBJECT_NONE, OBJECT_VEHICLE, u, tripoint::x, tripoint::y, and tripoint::z.

Referenced by walk_move().

◆ grabbed_veh_move()

bool game::grabbed_veh_move ( const tripoint dp)
private
Strength determines ability to drag vehicles Strength increases speed of dragging vehicles Strength decreases stamina cost of dragging vehicles

Definition at line 95 of file grab.cpp.

96{
97 const optional_vpart_position grabbed_vehicle_vp = m.veh_at( u.pos() + u.grab_point );
98 if( !grabbed_vehicle_vp ) {
99 add_msg( m_info, _( "No vehicle at grabbed point." ) );
100 u.grab( OBJECT_NONE );
101 return false;
102 }
103 vehicle *grabbed_vehicle = &grabbed_vehicle_vp->vehicle();
104 if( !grabbed_vehicle ||
105 !grabbed_vehicle->handle_potential_theft( u ) ) {
106 return false;
107 }
108 const int grabbed_part = grabbed_vehicle_vp->part_index();
109 for( int part_index = 0; part_index < grabbed_vehicle->part_count(); ++part_index ) {
110 monster *mon = grabbed_vehicle->get_pet( part_index );
111 if( mon != nullptr && mon->has_effect( effect_harnessed ) ) {
112 add_msg( m_info, _( "You cannot move this vehicle whilst your %s is harnessed!" ),
113 mon->get_name() );
114 u.grab( OBJECT_NONE );
115 return false;
116 }
117 }
118 const vehicle *veh_under_player = veh_pointer_or_null( m.veh_at( u.pos() ) );
119 if( grabbed_vehicle == veh_under_player ) {
120 u.grab_point = -dp;
121 return false;
122 }
123
124 tripoint dp_veh = -u.grab_point;
125 const tripoint prev_grab = u.grab_point;
126 tripoint next_grab = u.grab_point;
127
128 bool zigzag = false;
129
130 if( dp == prev_grab ) {
131 // We are pushing in the direction of vehicle
132 dp_veh = dp;
133 } else if( std::abs( dp.x + dp_veh.x ) != 2 && std::abs( dp.y + dp_veh.y ) != 2 ) {
134 // Not actually moving the vehicle, don't do the checks
135 u.grab_point = -( dp + dp_veh );
136 return false;
137 } else if( ( dp.x == prev_grab.x || dp.y == prev_grab.y ) &&
138 next_grab.x != 0 && next_grab.y != 0 ) {
139 // Zig-zag (or semi-zig-zag) pull: player is diagonal to vehicle
140 // and moves away from it, but not directly away
141 dp_veh.x = dp.x == -dp_veh.x ? 0 : dp_veh.x;
142 dp_veh.y = dp.y == -dp_veh.y ? 0 : dp_veh.y;
143
144 next_grab = -dp_veh;
145 zigzag = true;
146 } else {
147 // We are pulling the vehicle
148 next_grab = -dp;
149 }
150
151 // Make sure the mass and pivot point are correct
152 grabbed_vehicle->invalidate_mass();
153
154 //vehicle movement: strength check. very strong humans can move about 2,000 kg in a wheelbarrow.
155 // int str_req = grabbed_vehicle->total_mass() / 100_kilogram; //strength required to move vehicle.
156 // for smaller vehicles, offroad_str_req_cap sanity-checks our results.
157 int str_req = std::min( get_vehicle_str_requirement( grabbed_vehicle ),
158 offroad_str_req_cap( grabbed_vehicle ) );
159 int str = u.get_str();
160 if( u.is_mounted() ) {
161 auto mons = u.mounted_creature.get();
162 if( mons->has_flag( MF_RIDEABLE_MECH ) && mons->mech_str_addition() != 0 ) {
163 str = mons->mech_str_addition();
164 }
165 }
166 add_msg( m_debug, "str_req: %d", str_req );
167
168 //final strength check and outcomes
169 ///\EFFECT_STR determines ability to drag vehicles
170 if( str_req <= str ) {
171 if( !grabbed_vehicle->valid_wheel_config() ) {
172 make_scraping_noise( grabbed_vehicle->global_pos3(), str_req * 2 );
173 }
174
175 //calculate exertion factor and movement penalty
176 ///\EFFECT_STR increases speed of dragging vehicles
177 u.moves -= 400 * str_req / std::max( 1, str );
178 ///\EFFECT_STR decreases stamina cost of dragging vehicles
179 u.mod_stamina( -200 * str_req / std::max( 1, str ) );
180 const int ex = dice( 1, 6 ) - 1 + str_req;
181 if( ex > str + 1 ) {
182 // Pain and movement penalty if exertion exceeds character strength
183 add_msg( m_bad, _( "You strain yourself to move the %s!" ), grabbed_vehicle->name );
184 u.moves -= 200;
185 u.mod_pain( 1 );
186 } else if( ex >= str ) {
187 // Movement is slow if exertion nearly equals character strength
188 add_msg( _( "It takes some time to move the %s." ), grabbed_vehicle->name );
189 u.moves -= 200;
190 }
191 } else {
192 u.moves -= 100;
193 add_msg( m_bad, _( "You lack the strength to move the %s" ), grabbed_vehicle->name );
194 return true;
195 }
196
197 std::string blocker_name = _( "errors in movement code" );
198 const auto get_move_dir = [&]( const tripoint & dir, const tripoint & from ) {
199 tileray mdir;
200
201 mdir.init( dir.xy() );
202 grabbed_vehicle->turn( mdir.dir() - grabbed_vehicle->face.dir() );
203 grabbed_vehicle->face = grabbed_vehicle->turn_dir;
204 grabbed_vehicle->precalc_mounts( 1, mdir.dir(), grabbed_vehicle->pivot_point() );
205
206 // Grabbed part has to stay at distance 1 to the player
207 // and in roughly the same direction.
208 const tripoint new_part_pos = grabbed_vehicle->global_pos3() +
209 grabbed_vehicle->part( grabbed_part ).precalc[ 1 ];
210 const tripoint expected_pos = u.pos() + dp + from;
211 const tripoint actual_dir = expected_pos - new_part_pos;
212
213 grabbed_vehicle->adjust_zlevel( 1, dp );
214
215 // Set player location to illegal value so it can't collide with vehicle.
216 const tripoint player_prev = u.pos();
218 std::vector<veh_collision> colls;
219 const bool failed = grabbed_vehicle->collision( colls, actual_dir, true );
220 u.setpos( player_prev );
221 if( !colls.empty() ) {
222 blocker_name = colls.front().target_name;
223 }
224 return failed ? tripoint_zero : actual_dir;
225 };
226
227 // First try the move as intended
228 // But if that fails and the move is a zig-zag, try to recover:
229 // Try to place the vehicle in the position player just left rather than "flattening" the zig-zag
230 tripoint final_dp_veh = get_move_dir( dp_veh, next_grab );
231 if( final_dp_veh == tripoint_zero && zigzag ) {
232 final_dp_veh = get_move_dir( -prev_grab, -dp );
233 next_grab = -dp;
234 }
235
236 if( final_dp_veh == tripoint_zero ) {
237 add_msg( _( "The %s collides with %s." ), grabbed_vehicle->name, blocker_name );
238 u.grab_point = prev_grab;
239 return true;
240 }
241
242 u.grab_point = next_grab;
243
244 m.displace_vehicle( *grabbed_vehicle, final_dp_veh );
245
246 if( grabbed_vehicle ) {
247 grabbed_vehicle->shift_zlevel();
248 grabbed_vehicle->check_falling_or_floating();
249 } else {
250 debugmsg( "Grabbed vehicle disappeared" );
251 return false;
252 }
253
254 for( int p : grabbed_vehicle->wheelcache ) {
255 if( one_in( 2 ) ) {
256 tripoint wheel_p = grabbed_vehicle->global_part_pos3( grabbed_part );
257 grabbed_vehicle->handle_trap( wheel_p, p );
258 }
259 }
260
261 return false;
262
263}
void mod_stamina(int mod)
Definition: character.cpp:7108
bool displace_vehicle(vehicle &veh, const tripoint &dp)
Definition: map.cpp:1184
void init(point ad)
Definition: tileray.cpp:27
units::angle dir() const
Definition: tileray.cpp:74
void turn(units::angle deg)
void adjust_zlevel(int idir=0, const tripoint &offset=tripoint_zero)
tripoint global_pos3() const
Definition: vehicle.cpp:3283
bool valid_wheel_config() const
Definition: vehicle.cpp:4482
std::vector< int > wheelcache
Definition: vehicle.h:1550
void check_falling_or_floating()
point pivot_point() const
Definition: vehicle.cpp:5849
tileray face
Definition: vehicle.h:1680
void invalidate_mass()
Mark mass caches and pivot cache as dirty.
Definition: vehicle.cpp:6993
int part_count() const
Definition: vehicle.cpp:7100
bool collision(std::vector< veh_collision > &colls, const tripoint &dp, bool just_detect, bool bash_floor=false)
void precalc_mounts(int idir, units::angle dir, point pivot)
Definition: vehicle.cpp:3152
monster * get_pet(int p) const
Definition: vehicle.cpp:3264
vehicle_part & part(int part_num)
Definition: vehicle.cpp:7105
void handle_trap(const tripoint &p, int part)
tripoint global_part_pos3(const int &index) const
Get the coordinates of the studied part of the vehicle.
Definition: vehicle.cpp:3288
void shift_zlevel()
units::angle turn_dir
Definition: vehicle.h:1659
static const efftype_id effect_harnessed("harnessed")
auto offroad_str_req_cap(vehicle *veh) -> int
Definition: grab.cpp:42
auto get_vehicle_str_requirement(vehicle *veh) -> int
Definition: grab.cpp:78
auto make_scraping_noise(const tripoint &pos, const int volume) -> void
Definition: grab.cpp:29
static constexpr tripoint tripoint_zero
Definition: point.h:259
int dice(int number, int sides)
Definition: rng.cpp:85
std::array< tripoint, 2 > precalc
mount translated to face.dir [0] and turn_dir [1]
Definition: vehicle_part.h:210

References _, add_msg(), vehicle::adjust_zlevel(), vehicle::check_falling_or_floating(), vehicle::collision(), debugmsg, dice(), tileray::dir(), map::displace_vehicle(), effect_harnessed, vehicle::face, failed, monster::get_name(), vehicle::get_pet(), Character::get_str(), anonymous_namespace{grab.cpp}::get_vehicle_str_requirement(), vehicle::global_part_pos3(), vehicle::global_pos3(), avatar::grab(), player::grab_point, vehicle::handle_potential_theft(), vehicle::handle_trap(), Creature::has_effect(), tileray::init(), vehicle::invalidate_mass(), Character::is_mounted(), m, m_bad, m_debug, m_info, anonymous_namespace{grab.cpp}::make_scraping_noise(), MF_RIDEABLE_MECH, Character::mod_pain(), Character::mod_stamina(), Character::mounted_creature, Creature::moves, vehicle::name, OBJECT_NONE, anonymous_namespace{grab.cpp}::offroad_str_req_cap(), one_in(), vehicle::part(), vehicle::part_count(), vehicle::pivot_point(), Character::pos(), vehicle_part::precalc, vehicle::precalc_mounts(), Character::setpos(), vehicle::shift_zlevel(), tripoint_zero, vehicle::turn(), vehicle::turn_dir, u, vehicle::valid_wheel_config(), map::veh_at(), veh_pointer_or_null(), vehicle::wheelcache, tripoint::x, tripoint::xy(), and tripoint::y.

Referenced by grabbed_move().

◆ handle_action()

bool game::handle_action ( )
private

Definition at line 1529 of file handle_action.cpp.

1530{
1531 std::string action;
1532 input_context ctxt;
1534 user_turn current_turn;
1535 // Check if we have an auto-move destination
1536 if( u.has_destination() ) {
1538 if( act == ACTION_NULL ) {
1539 add_msg( m_info, _( "Auto-move canceled" ) );
1541 return false;
1542 }
1543 } else if( u.has_destination_activity() ) {
1544 // starts destination activity after the player successfully reached his destination
1546 return false;
1547 } else {
1548 // No auto-move, ask player for input
1549 ctxt = get_player_input( action );
1550 }
1551
1552 const optional_vpart_position vp = m.veh_at( u.pos() );
1553 bool veh_ctrl = !u.is_dead_state() &&
1554 ( ( vp && vp->vehicle().player_in_control( u ) ) || remoteveh() != nullptr );
1555
1556 // If performing an action with right mouse button, co-ordinates
1557 // of location clicked.
1558 std::optional<tripoint> mouse_target;
1559
1560 if( uquit == QUIT_WATCH && action == "QUIT" ) {
1561 uquit = QUIT_DIED;
1562 return false;
1563 }
1564
1565 if( act == ACTION_NULL ) {
1567
1568 if( act == ACTION_KEYBINDINGS ) {
1569 // already handled by input context
1570 return false;
1571 }
1572
1573 if( act == ACTION_MAIN_MENU ) {
1574 if( uquit == QUIT_WATCH ) {
1575 return false;
1576 }
1577 // No auto-move actions have or can be set at this point.
1579 destination_preview.clear();
1581 if( act == ACTION_NULL ) {
1582 return false;
1583 }
1584 }
1585
1586 if( act == ACTION_ACTIONMENU ) {
1587 if( uquit == QUIT_WATCH ) {
1588 return false;
1589 }
1590 // No auto-move actions have or can be set at this point.
1592 destination_preview.clear();
1594 if( act == ACTION_NULL ) {
1595 return false;
1596 }
1597#if defined(__ANDROID__)
1598 if( get_option<bool>( "ANDROID_ACTIONMENU_AUTOADD" ) && ctxt.get_category() == "DEFAULTMODE" ) {
1599 add_best_key_for_action_to_quick_shortcuts( act, ctxt.get_category(), false );
1600 }
1601#endif
1602 }
1603
1604 if( act == ACTION_KEYBINDINGS ) {
1606 destination_preview.clear();
1607 act = ctxt.display_menu( true );
1608 if( act == ACTION_NULL ) {
1609 return false;
1610 }
1611 }
1612
1615 }
1616
1617 if( act == ACTION_SELECT || act == ACTION_SEC_SELECT ) {
1618 // Mouse button click
1619 if( veh_ctrl ) {
1620 // No mouse use in vehicle
1621 return false;
1622 }
1623
1624 if( u.is_dead_state() ) {
1625 // do not allow mouse actions while dead
1626 return false;
1627 }
1628
1629 const std::optional<tripoint> mouse_pos = ctxt.get_coordinates( w_terrain );
1630 if( !mouse_pos ) {
1631 return false;
1632 } else if( !u.sees( *mouse_pos ) ) {
1633 // Not clicked in visible terrain
1634 return false;
1635 }
1636 mouse_target = mouse_pos;
1637
1638 if( act == ACTION_SELECT ) {
1639 // Note: The following has the potential side effect of
1640 // setting auto-move destination state in addition to setting
1641 // act.
1642 if( !try_get_left_click_action( act, *mouse_target ) ) {
1643 return false;
1644 }
1645 } else if( act == ACTION_SEC_SELECT ) {
1646 if( !try_get_right_click_action( act, *mouse_target ) ) {
1647 return false;
1648 }
1649 }
1650 } else if( act != ACTION_TIMEOUT ) {
1651 // act has not been set for an auto-move, so clearing possible
1652 // auto-move destinations. Since initializing an auto-move with
1653 // the mouse may span across multiple actions, we do not clear the
1654 // auto-move destination if the action is only a timeout, as this
1655 // would require the user to double click quicker than the
1656 // timeout delay.
1658 destination_preview.clear();
1659 }
1660 }
1661
1662 if( act == ACTION_NULL ) {
1663 const input_event &&evt = ctxt.get_raw_input();
1664 if( !evt.sequence.empty() ) {
1665 const int ch = evt.get_first_input();
1666 const std::string &&name = inp_mngr.get_keyname( ch, evt.type, true );
1667 if( !get_option<bool>( "NO_UNKNOWN_COMMAND_MSG" ) ) {
1668 add_msg( m_info, _( "Unknown command: \"%s\" (%ld)" ), name, ch );
1669 if( const std::optional<std::string> hint =
1671 add_msg( m_info, _( "%s at any time to see and edit keybindings relevant to "
1672 "the current context." ),
1673 *hint );
1674 }
1675 }
1676 }
1677 return false;
1678 }
1679
1680 // This has no action unless we're in a special game mode.
1681 gamemode->pre_action( act );
1682
1683 int soffset = get_option<int>( "MOVE_VIEW_OFFSET" );
1684
1685 int before_action_moves = u.moves;
1686
1687 // These actions are allowed while deathcam is active. Registered in game::get_player_input
1688 if( uquit == QUIT_WATCH || !u.is_dead_state() ) {
1689 switch( act ) {
1692 break;
1693
1694 case ACTION_CENTER:
1697 break;
1698
1699 case ACTION_SHIFT_N:
1700 case ACTION_SHIFT_NE:
1701 case ACTION_SHIFT_E:
1702 case ACTION_SHIFT_SE:
1703 case ACTION_SHIFT_S:
1704 case ACTION_SHIFT_SW:
1705 case ACTION_SHIFT_W:
1706 case ACTION_SHIFT_NW: {
1707 static const std::map<action_id, std::pair<point, point>> shift_delta = {
1716 };
1718 shift_delta.at( act ).second * soffset : shift_delta.at( act ).first * soffset;
1719 }
1720 break;
1721
1722 case ACTION_LOOK:
1723 look_around();
1724 break;
1725
1726 case ACTION_KEYBINDINGS:
1727 // already handled by input context
1728 break;
1729
1730 default:
1731 break;
1732 }
1733 }
1734
1735 // actions allowed only while alive
1736 if( !u.is_dead_state() ) {
1737 switch( act ) {
1738 case ACTION_NULL:
1739 case NUM_ACTIONS:
1740 break; // dummy entries
1741 case ACTION_ACTIONMENU:
1742 case ACTION_MAIN_MENU:
1743 case ACTION_KEYBINDINGS:
1744 break; // handled above
1745
1746 case ACTION_TIMEOUT:
1747 if( check_safe_mode_allowed( false ) ) {
1749 }
1750 break;
1751
1752 case ACTION_PAUSE:
1753 if( check_safe_mode_allowed() ) {
1755 }
1756 break;
1757
1758 case ACTION_CYCLE_MOVE:
1760 break;
1761
1762 case ACTION_RESET_MOVE:
1764 break;
1765
1766 case ACTION_TOGGLE_RUN:
1768 break;
1769
1772 break;
1773
1776 break;
1777
1778 case ACTION_MOVE_FORTH:
1780 case ACTION_MOVE_RIGHT:
1782 case ACTION_MOVE_BACK:
1784 case ACTION_MOVE_LEFT:
1786 if( !u.get_value( "remote_controlling" ).empty() &&
1790 } else if( veh_ctrl ) {
1791 // vehicle control uses x for steering and y for ac/deceleration,
1792 // so no rotation needed
1794 } else {
1796 if( auto_travel_mode && !u.is_auto_moving() ) {
1797 for( int i = 0; i < SEEX; i++ ) {
1798 tripoint auto_travel_destination( u.posx() + dest_delta.x * ( SEEX - i ),
1799 u.posy() + dest_delta.y * ( SEEX - i ),
1800 u.posz() );
1802 auto_travel_destination,
1804 u.get_path_avoid() );
1805 if( !destination_preview.empty() ) {
1808 break;
1809 }
1810 }
1813 if( dest_next == point_zero ) {
1815 }
1816 dest_delta = dest_next;
1817 }
1818 if( !avatar_action::move( u, m, dest_delta ) ) {
1819 // auto-move should be canceled due to a failed move or obstacle
1821 }
1822 }
1823 break;
1824 case ACTION_MOVE_DOWN:
1825 if( u.is_mounted() ) {
1826 auto mon = u.mounted_creature.get();
1827 if( !mon->has_flag( MF_RIDEABLE_MECH ) ) {
1828 add_msg( m_info, _( "You can't go down stairs while you're riding." ) );
1829 break;
1830 }
1831 }
1832 if( !u.in_vehicle ) {
1833 vertical_move( -1, false );
1834 } else if( veh_ctrl && vp->vehicle().is_rotorcraft() ) {
1836 }
1837 break;
1838
1839 case ACTION_MOVE_UP:
1840 if( u.is_mounted() ) {
1841 auto mon = u.mounted_creature.get();
1842 if( !mon->has_flag( MF_RIDEABLE_MECH ) ) {
1843 add_msg( m_info, _( "You can't go down stairs while you're riding." ) );
1844 break;
1845 }
1846 }
1847 if( !u.in_vehicle ) {
1848 vertical_move( 1, false );
1849 } else if( veh_ctrl && vp->vehicle().is_rotorcraft() ) {
1851 } else if( veh_ctrl && vp->vehicle().has_part( "ROTOR" ) &&
1852 !vp->vehicle().has_sufficient_rotorlift() ) {
1853 add_msg( m_bad, _( "The rotors struggle to generate enough lift!" ) );
1854 }
1855 break;
1856
1857 case ACTION_OPEN:
1859 add_msg( m_info, _( "You can't open things while you're in your shell." ) );
1860 } else if( u.is_mounted() ) {
1861 auto mon = u.mounted_creature.get();
1862 if( !mon->has_flag( MF_RIDEABLE_MECH ) ) {
1863 add_msg( m_info, _( "You can't open things while you're riding." ) );
1864 break;
1865 } else {
1866 open();
1867 }
1868 } else {
1869 open();
1870 }
1871 break;
1872
1873 case ACTION_CLOSE:
1875 add_msg( m_info, _( "You can't close things while you're in your shell." ) );
1876 } else if( u.is_mounted() ) {
1877 auto mon = u.mounted_creature.get();
1878 if( !mon->has_flag( MF_RIDEABLE_MECH ) ) {
1879 add_msg( m_info, _( "You can't close things while you're riding." ) );
1880 break;
1881 } else {
1882 close();
1883 }
1884 } else if( mouse_target ) {
1885 doors::close_door( m, u, *mouse_target );
1886 } else {
1887 close();
1888 }
1889 break;
1890
1891 case ACTION_SMASH:
1892 if( veh_ctrl ) {
1893 handbrake();
1894 } else if( u.has_active_mutation( trait_SHELL2 ) ) {
1895 add_msg( m_info, _( "You can't smash things while you're in your shell." ) );
1896 } else {
1897 smash();
1898 }
1899 break;
1900
1901 case ACTION_EXAMINE:
1903 add_msg( m_info, _( "You can't examine your surroundings while you're in your shell." ) );
1904 } else if( mouse_target ) {
1905 examine( *mouse_target );
1906 } else {
1907 examine();
1908 }
1909 break;
1910
1911 case ACTION_ADVANCEDINV:
1913 add_msg( m_info, _( "You can't move mass quantities while you're in your shell." ) );
1914 } else if( u.is_mounted() ) {
1915 add_msg( m_info, _( "You can't move mass quantities while you're riding." ) );
1916 } else {
1918 }
1919 break;
1920
1921 case ACTION_PICKUP:
1923 add_msg( m_info, _( "You can't pick anything up while you're in your shell." ) );
1924 } else if( u.is_mounted() ) {
1925 add_msg( m_info, _( "You can't pick anything up while you're riding." ) );
1926 } else if( mouse_target ) {
1927 pickup( *mouse_target );
1928 } else {
1929 pickup();
1930 }
1931 break;
1932
1933 case ACTION_PICKUP_FEET:
1935 add_msg( m_info, _( "You can't pick anything up while you're in your shell." ) );
1936 } else {
1937 pickup_feet();
1938 }
1939 break;
1940
1941 case ACTION_GRAB:
1943 add_msg( m_info, _( "You can't grab things while you're in your shell." ) );
1944 } else if( u.is_mounted() ) {
1945 auto mon = u.mounted_creature.get();
1946 if( !mon->has_flag( MF_RIDEABLE_MECH ) ) {
1947 add_msg( m_info, _( "You can't grab things while you're riding." ) );
1948 break;
1949 } else if( !mon->type->mech_weapon.is_empty() ) {
1950 add_msg( m_info, _( "Your mech doesn't have hands to grab with." ) );
1951 break;
1952 } else {
1953 grab();
1954 }
1955 } else {
1956 grab();
1957 }
1958 break;
1959
1960 case ACTION_HAUL:
1962 add_msg( m_info, _( "You can't haul things while you're in your shell." ) );
1963 } else if( u.is_mounted() ) {
1964 add_msg( m_info, _( "You can't haul things while you're riding." ) );
1965 } else {
1966 haul();
1967 }
1968 break;
1969
1970 case ACTION_BUTCHER:
1972 add_msg( m_info, _( "You can't butcher while you're in your shell." ) );
1973 } else if( u.is_mounted() ) {
1974 add_msg( m_info, _( "You can't butcher while you're riding." ) );
1975 } else {
1976 butcher();
1977 }
1978 break;
1979
1980 case ACTION_CHAT:
1981 chat();
1982 break;
1983
1984 case ACTION_PEEK:
1986 add_msg( m_info, _( "You can't peek around corners while you're in your shell." ) );
1987 } else if( u.is_mounted() ) {
1988 add_msg( m_info, _( "You can't peek around corners while you're riding." ) );
1989 } else {
1990 peek();
1991 }
1992 break;
1993
1994 case ACTION_LIST_ITEMS:
1996 break;
1997
1998 case ACTION_ZONES:
1999 zones_manager();
2000 break;
2001
2002 case ACTION_LOOT:
2003 loot();
2004 break;
2005
2006 case ACTION_INVENTORY:
2008 break;
2009
2010 case ACTION_COMPARE:
2011 game_menus::inv::compare( u, std::nullopt );
2012 break;
2013
2014 case ACTION_ORGANIZE:
2016 break;
2017
2018 case ACTION_USE:
2019 // Shell-users are presumed to be able to mess with their inventories, etc
2020 // while in the shell. Eating, gear-changing, and item use are OK.
2022 break;
2023
2024 case ACTION_USE_WIELDED:
2026 break;
2027
2028 case ACTION_WEAR:
2029 wear();
2030 break;
2031
2032 case ACTION_TAKE_OFF:
2033 takeoff();
2034 break;
2035
2036 case ACTION_EAT:
2037 if( !avatar_action::eat_here( u ) ) {
2039 }
2040 break;
2041
2043 if( !avatar_action::eat_here( u ) ) {
2045 }
2046 break;
2047
2048 case ACTION_READ:
2049 // Shell-users are presumed to have the book just at an opening and read it that way
2050 read();
2051 break;
2052
2053 case ACTION_WIELD:
2055 break;
2056
2057 case ACTION_PICK_STYLE:
2058 u.martial_arts_data->pick_style( u );
2059 break;
2060
2061 case ACTION_RELOAD_ITEM:
2063 break;
2064
2067 break;
2068
2071 break;
2072
2073 case ACTION_UNLOAD:
2075 break;
2076
2077 case ACTION_MEND:
2079 break;
2080
2081 case ACTION_THROW: {
2082 item_location loc;
2083 avatar_action::plthrow( g->u, loc );
2084 break;
2085 }
2086
2087 case ACTION_FIRE:
2088 fire();
2089 break;
2090
2091 case ACTION_CAST_SPELL:
2092 cast_spell();
2093 break;
2094
2095 case ACTION_FIRE_BURST: {
2096 if( u.primary_weapon().gun_set_mode( gun_mode_id( "AUTO" ) ) ) {
2098 }
2099 break;
2100 }
2101
2103 if( u.is_armed() && u.primary_weapon().is_gun() && !u.primary_weapon().is_gunmod() ) {
2104 if( u.primary_weapon().gun_all_modes().size() > 1 ) {
2106 } else {
2107 add_msg( m_info, _( "Your %s has only one firing mode." ), u.primary_weapon().display_name() );
2108 }
2109 }
2110 break;
2111
2113 if( u.is_armed() && u.primary_weapon().is_gun() && !u.primary_weapon().is_gunmod() ) {
2115 }
2116 break;
2117
2118 case ACTION_DROP:
2119 // You CAN drop things to your own tile while in the shell.
2120 drop();
2121 break;
2122
2123 case ACTION_DIR_DROP:
2125 add_msg( m_info, _( "You can't drop things to another tile while you're in your shell." ) );
2126 } else {
2128 }
2129 break;
2130 case ACTION_BIONICS:
2131 show_bionics_ui( u );
2132 break;
2133 case ACTION_MUTATIONS:
2135 break;
2136
2137 case ACTION_SORT_ARMOR:
2139 break;
2140
2141 case ACTION_WAIT:
2142 wait();
2143 break;
2144
2145 case ACTION_CRAFT:
2147 add_msg( m_info, _( "You can't craft while you're in your shell." ) );
2148 } else if( u.is_mounted() ) {
2149 add_msg( m_info, _( "You can't craft while you're riding." ) );
2150 } else {
2151 u.craft();
2152 }
2153 break;
2154
2155 case ACTION_RECRAFT:
2157 add_msg( m_info, _( "You can't craft while you're in your shell." ) );
2158 } else if( u.is_mounted() ) {
2159 add_msg( m_info, _( "You can't craft while you're riding." ) );
2160 } else {
2161 u.recraft();
2162 }
2163 break;
2164
2165 case ACTION_LONGCRAFT:
2167 add_msg( m_info, _( "You can't craft while you're in your shell." ) );
2168 } else if( u.is_mounted() ) {
2169 add_msg( m_info, _( "You can't craft while you're riding." ) );
2170 } else {
2171 u.long_craft();
2172 }
2173 break;
2174
2175 case ACTION_DISASSEMBLE:
2176 if( u.controlling_vehicle ) {
2177 add_msg( m_info, _( "You can't disassemble items while driving." ) );
2178 } else if( u.is_mounted() ) {
2179 add_msg( m_info, _( "You can't disassemble items while you're riding." ) );
2180 } else {
2182 }
2183 break;
2184
2185 case ACTION_CONSTRUCT:
2186 if( u.in_vehicle ) {
2187 add_msg( m_info, _( "You can't construct while in a vehicle." ) );
2188 } else if( u.has_active_mutation( trait_SHELL2 ) ) {
2189 add_msg( m_info, _( "You can't construct while you're in your shell." ) );
2190 } else if( u.is_mounted() ) {
2191 add_msg( m_info, _( "You can't construct while you're riding." ) );
2192 } else {
2193 construction_menu( false );
2194 }
2195 break;
2196
2197 case ACTION_SLEEP:
2198 if( veh_ctrl ) {
2199 add_msg( m_info, _( "Vehicle control has moved, %s" ),
2200 press_x( ACTION_CONTROL_VEHICLE, _( "new binding is " ),
2201 _( "new default binding is '^'." ) ) );
2202 } else {
2203 sleep();
2204 }
2205 break;
2206
2209 add_msg( m_info, _( "You can't operate a vehicle while you're in your shell." ) );
2210 } else if( u.is_mounted() ) {
2211 u.dismount();
2212 } else {
2214 }
2215 break;
2216
2219 add_msg( m_info, auto_travel_mode ? _( "Auto travel mode ON!" ) : _( "Auto travel mode OFF!" ) );
2220 break;
2221
2223 if( safe_mode == SAFE_MODE_OFF ) {
2225 mostseen = 0;
2226 add_msg( m_info, _( "Safe mode ON!" ) );
2227 } else {
2230 add_msg( m_info, get_option<bool>( "AUTOSAFEMODE" )
2231 ? _( "Safe mode OFF! (Auto safe mode still enabled!)" ) : _( "Safe mode OFF!" ) );
2232 }
2236 }
2237 break;
2238
2240 auto &autosafemode_option = get_options().get_option( "AUTOSAFEMODE" );
2241 add_msg( m_info, autosafemode_option.value_as<bool>()
2242 ? _( "Auto safe mode OFF!" ) : _( "Auto safe mode ON!" ) );
2243 autosafemode_option.setNext();
2244 break;
2245 }
2246
2248 if( safe_mode == SAFE_MODE_STOP ) {
2249 add_msg( m_info, _( "Ignoring enemy!" ) );
2250 for( auto &elem : u.get_mon_visible().new_seen_mon ) {
2251 monster &critter = *elem;
2252 critter.ignoring = rl_dist( u.pos(), critter.pos() );
2253 }
2255 } else if( u.has_effect( effect_laserlocked ) ) {
2256 if( u.has_trait( trait_PROF_CHURL ) ) {
2257 add_msg( m_warning, _( "You make the sign of the cross." ) );
2258 } else {
2259 add_msg( m_info, _( "Ignoring laser targeting!" ) );
2260 }
2263 }
2264 break;
2265
2267 if( safe_mode == SAFE_MODE_STOP && !get_safemode().empty() ) {
2269 add_msg( m_info, _( "Creature whitelisted: %s" ), get_safemode().lastmon_whitelist );
2271 mostseen = 0;
2272 } else {
2273 get_safemode().show();
2274 }
2275 break;
2276
2277 case ACTION_SUICIDE:
2278 if( query_yn( _( "Commit suicide?" ) ) ) {
2279 if( query_yn( _( "REALLY commit suicide?" ) ) ) {
2280 u.apply_damage( &u, body_part_head, 99999 );
2281 u.moves = 0;
2282 u.place_corpse();
2284 }
2285 }
2286 break;
2287
2288 case ACTION_SAVE:
2289 if( query_yn( _( "Save and quit?" ) ) ) {
2290 if( save() ) {
2291 u.moves = 0;
2292 uquit = QUIT_SAVED;
2293 }
2294 }
2295 break;
2296
2297 case ACTION_QUICKSAVE:
2298 quicksave();
2299 return false;
2300
2301 case ACTION_QUICKLOAD:
2302 quickload();
2303 return false;
2304
2305 case ACTION_PL_INFO:
2307 break;
2308
2309 case ACTION_MAP:
2311 break;
2312
2313 case ACTION_SKY:
2314 if( m.is_outside( u.pos() ) ) {
2316 } else {
2317 add_msg( m_info, _( "You can't see the sky from here." ) );
2318 }
2319 break;
2320
2321 case ACTION_MISSIONS:
2322 list_missions();
2323 break;
2324
2325 case ACTION_SCORES:
2327 break;
2328
2329 case ACTION_DIARY:
2331 break;
2332
2333 case ACTION_FACTIONS:
2334 faction_manager_ptr->display();
2335 break;
2336
2337 case ACTION_MORALE:
2338 u.disp_morale();
2339 break;
2340
2341 case ACTION_MESSAGES:
2343 break;
2344
2345 case ACTION_HELP:
2347 break;
2348
2349 case ACTION_OPTIONS:
2350 get_options().show( true );
2351 break;
2352
2353 case ACTION_AUTOPICKUP:
2355 break;
2356
2357 case ACTION_AUTONOTES:
2359 break;
2360
2361 case ACTION_SAFEMODE:
2362 get_safemode().show();
2363 break;
2364
2367 break;
2368
2369 case ACTION_COLOR:
2370 all_colors.show_gui();
2371 break;
2372
2373 case ACTION_WORLD_MODS:
2374 world_generator->show_active_world_mods( world_generator->active_world->active_mod_order );
2375 break;
2376
2377 case ACTION_DEBUG:
2379 break; //don't do anything when sharing and not debugger
2380 }
2382 break;
2383
2384 case ACTION_LUA_CONSOLE:
2386 break;
2387
2388 case ACTION_LUA_RELOAD:
2390 break;
2391
2394 break;
2395
2398 break;
2399
2402 break;
2403
2405 reload_tileset( []( std::string str ) {
2406 DebugLog( DL::Info, DC::Main ) << str;
2407 } );
2408 break;
2409
2411 get_options().get_option( "AUTO_FEATURES" ).setNext();
2412 get_options().save();
2413 //~ Auto Features are now ON/OFF
2414 add_msg( _( "%s are now %s." ),
2415 get_options().get_option( "AUTO_FEATURES" ).getMenuText(),
2416 get_option<bool>( "AUTO_FEATURES" ) ? _( "ON" ) : _( "OFF" ) );
2417 break;
2418
2420 get_options().get_option( "AUTO_PULP_BUTCHER" ).setNext();
2421 get_options().save();
2422 //~ Auto Pulp/Pulp Adjacent/Butcher is now set to x
2423 add_msg( _( "%s is now set to %s." ),
2424 get_options().get_option( "AUTO_PULP_BUTCHER" ).getMenuText(),
2425 get_options().get_option( "AUTO_PULP_BUTCHER" ).getValueName() );
2426 break;
2427
2429 get_options().get_option( "AUTO_MINING" ).setNext();
2430 get_options().save();
2431 //~ Auto Mining is now ON/OFF
2432 add_msg( _( "%s is now %s." ),
2433 get_options().get_option( "AUTO_MINING" ).getMenuText(),
2434 get_option<bool>( "AUTO_MINING" ) ? _( "ON" ) : _( "OFF" ) );
2435 break;
2436
2438 if( g->u.get_value( "THIEF_MODE" ) == "THIEF_ASK" ) {
2439 u.set_value( "THIEF_MODE", "THIEF_HONEST" );
2440 u.set_value( "THIEF_MODE_KEEP", "YES" );
2441 //~ Thief mode cycled between THIEF_ASK/THIEF_HONEST/THIEF_STEAL
2442 add_msg( _( "You will not pick up other peoples belongings." ) );
2443 } else if( g->u.get_value( "THIEF_MODE" ) == "THIEF_HONEST" ) {
2444 u.set_value( "THIEF_MODE", "THIEF_STEAL" );
2445 u.set_value( "THIEF_MODE_KEEP", "YES" );
2446 //~ Thief mode cycled between THIEF_ASK/THIEF_HONEST/THIEF_STEAL
2447 add_msg( _( "You will pick up also those things that belong to others!" ) );
2448 } else if( g->u.get_value( "THIEF_MODE" ) == "THIEF_STEAL" ) {
2449 u.set_value( "THIEF_MODE", "THIEF_ASK" );
2450 u.set_value( "THIEF_MODE_KEEP", "NO" );
2451 //~ Thief mode cycled between THIEF_ASK/THIEF_HONEST/THIEF_STEAL
2452 add_msg( _( "You will be reminded not to steal." ) );
2453 } else {
2454 // ERROR
2455 add_msg( _( "THIEF_MODE CONTAINED BAD VALUE [ %s ]!" ), g->u.get_value( "THIEF_MODE" ) );
2456 }
2457 break;
2458
2460 get_options().get_option( "AUTO_FORAGING" ).setNext();
2461 get_options().save();
2462 //~ Auto Foraging is now set to x
2463 add_msg( _( "%s is now set to %s." ),
2464 get_options().get_option( "AUTO_FORAGING" ).getMenuText(),
2465 get_options().get_option( "AUTO_FORAGING" ).getValueName() );
2466 break;
2467
2469 get_options().get_option( "AUTO_PICKUP" ).setNext();
2470 get_options().save();
2471 //~ Auto pickup is now set to x
2472 add_msg( _( "%s is now set to %s." ),
2473 get_options().get_option( "AUTO_PICKUP" ).getMenuText(),
2474 get_options().get_option( "AUTO_PICKUP" ).getValueName() );
2475 break;
2476
2479 break; //don't do anything when sharing and not debugger
2480 }
2481 display_scent();
2482 break;
2483
2486 break; //don't do anything when sharing and not debugger
2487 }
2488 display_scent();
2489 break;
2490
2493 break; //don't do anything when sharing and not debugger
2494 }
2496 break;
2499 break; //don't do anything when sharing and not debugger
2500 }
2502 break;
2505 break; //don't do anything when sharing and not debugger
2506 }
2508 break;
2509
2512 break; //don't do anything when sharing and not debugger
2513 }
2515 break;
2516
2519 break; //don't do anything when sharing and not debugger
2520 }
2522 break;
2523
2526 break; //don't do anything when sharing and not debugger
2527 }
2529 break;
2530
2532 g->debug_submap_grid_overlay = !g->debug_submap_grid_overlay;
2533 break;
2534
2537 break;
2538
2541 break; //don't do anything when sharing and not debugger
2542 }
2544 if( debug_mode ) {
2545 add_msg( m_info, _( "Debug mode ON!" ) );
2546 } else {
2547 add_msg( m_info, _( "Debug mode OFF!" ) );
2548 }
2549 break;
2550
2551 case ACTION_ZOOM_IN:
2552 zoom_in();
2554 break;
2555
2556 case ACTION_ZOOM_OUT:
2557 zoom_out();
2559 break;
2560
2561 case ACTION_ITEMACTION:
2563 break;
2564
2565 case ACTION_AUTOATTACK:
2567 break;
2568
2569 default:
2570 break;
2571 }
2572 }
2573 if( act != ACTION_TIMEOUT ) {
2574 u.mod_moves( -current_turn.moves_elapsed() );
2575 }
2576 gamemode->post_action( act );
2577
2578 u.movecounter = ( !u.is_dead_state() ? ( before_action_moves - u.moves ) : 0 );
2579 dbg( DL::Info ) << string_format( "%s: [%d] %d - %d = %d", action_ident( act ),
2580 to_turn<int>( calendar::turn ), before_action_moves, u.movecounter, u.moves );
2581 return ( !u.is_dead_state() );
2582}
bool can_action_change_worldstate(const action_id act)
Lookup whether an action can affect the state of the game world.
Definition: action.cpp:358
action_id look_up_action(const std::string &ident)
Lookup an action ID by its unique string identifier.
Definition: action.cpp:431
action_id handle_main_menu()
Show in-game main menu.
Definition: action.cpp:919
point get_delta_from_movement_action(const action_id act, const iso_rotate rot)
Definition: action.cpp:520
std::optional< std::string > press_x_if_bound(action_id act)
Definition: action.cpp:482
action_id handle_action_menu()
Show the action menu.
Definition: action.cpp:695
@ ACTION_SAFEMODE
Open safemode manager.
Definition: action.h:263
@ ACTION_PEEK
Peek through something (e.g.
Definition: action.h:117
@ ACTION_OPEN
Open an item (e.g.
Definition: action.h:95
@ ACTION_CRAFT
Open crafting menu.
Definition: action.h:195
@ ACTION_DROP
Open the drop-item menu.
Definition: action.h:177
@ ACTION_READ
Open the read menu.
Definition: action.h:149
@ ACTION_TOGGLE_AUTO_PICKUP
Turn auto pickup on/off.
Definition: action.h:313
@ ACTION_MOVE_BACK_LEFT
Move towards bottom-left of screen / decelerate and steer left.
Definition: action.h:47
@ ACTION_ZOOM_IN
Zoom view out.
Definition: action.h:291
@ ACTION_EAT
Open the default consume item menu.
Definition: action.h:145
@ ACTION_SMASH
Smash something.
Definition: action.h:99
@ ACTION_ADVANCEDINV
Open the advanced inventory screen.
Definition: action.h:131
@ ACTION_LUA_RELOAD
Hot-reload Lua code.
Definition: action.h:281
@ ACTION_QUICKSAVE
Quicksave the game.
Definition: action.h:223
@ ACTION_HELP
Display help screen.
Definition: action.h:249
@ ACTION_MESSAGES
Display messages screen.
Definition: action.h:247
@ ACTION_ZONES
Open the zone manager.
Definition: action.h:121
@ ACTION_TOGGLE_PIXEL_MINIMAP
Turn pixel minimap on/off.
Definition: action.h:297
@ ACTION_USE
Open the use menu.
Definition: action.h:137
@ ACTION_QUICKLOAD
Quickload the game.
Definition: action.h:225
@ ACTION_LIST_ITEMS
List items and monsters in a given square.
Definition: action.h:119
@ ACTION_DEBUG
Open debug menu.
Definition: action.h:277
@ ACTION_OPTIONS
Display options window.
Definition: action.h:257
@ ACTION_MOVE_FORTH
Move towards top of screen / accelerate.
Definition: action.h:37
@ ACTION_PICK_STYLE
Open the martial-arts style menu.
Definition: action.h:153
@ ACTION_CONSTRUCT
Open construct menu.
Definition: action.h:201
@ ACTION_MOVE_FORTH_RIGHT
Move towards top-right of screen / accelerate and steer right.
Definition: action.h:39
@ ACTION_SORT_ARMOR
Open the armor sorting menu.
Definition: action.h:185
@ ACTION_OPEN_CONSUME
Open the custom consume item menu.
Definition: action.h:147
@ ACTION_MORALE
Display morale effects screen.
Definition: action.h:245
@ ACTION_NULL
Invalid action used for various lookup errors.
Definition: action.h:20
@ ACTION_RESET_MOVE
Reset movement mode to walk
Definition: action.h:59
@ ACTION_CHAT
Chat with something.
Definition: action.h:113
@ ACTION_RELOAD_WIELDED
Attempt to reload wielded object.
Definition: action.h:159
@ ACTION_MOVE_DOWN
Descend a staircase.
Definition: action.h:53
@ ACTION_MISSIONS
Display missions screen.
Definition: action.h:239
@ ACTION_AUTONOTES
Open autonotes manager.
Definition: action.h:261
@ ACTION_WIELD
Open the wield menu.
Definition: action.h:151
@ ACTION_THROW
Open the throw menu.
Definition: action.h:165
@ ACTION_TOGGLE_AUTO_MINING
Turn auto mining on/off.
Definition: action.h:309
@ ACTION_INVENTORY
Open the primary inventory screen.
Definition: action.h:129
@ ACTION_TOGGLE_AUTOSAFE
Turn automatic triggering of safemode on/off.
Definition: action.h:213
@ ACTION_OPEN_MOVEMENT
Open movement mode menu.
Definition: action.h:65
@ ACTION_COMPARE
Open the item compare screen.
Definition: action.h:133
@ ACTION_SCORES
Display scores screen.
Definition: action.h:241
@ ACTION_BUTCHER
Butcher or disassemble objects in current square.
Definition: action.h:111
@ ACTION_SEC_SELECT
Click on a point with secondary mouse button (usually right button)
Definition: action.h:27
@ ACTION_TOGGLE_CROUCH
Toggle crouch on/off.
Definition: action.h:63
@ ACTION_TOGGLE_HOUR_TIMER
Toggle timing of the game hours.
Definition: action.h:329
@ ACTION_SELECT
Click on a point with primary mouse button (usually left button)
Definition: action.h:25
@ ACTION_MAIN_MENU
Display main menu.
Definition: action.h:251
@ ACTION_DISPLAY_SUBMAP_GRID
Toggle submap grid overlay.
Definition: action.h:327
@ ACTION_WAIT
Open wait menu.
Definition: action.h:193
@ ACTION_ACTIONMENU
Open the action menu.
Definition: action.h:293
@ ACTION_DISASSEMBLE
Open disassemble menu.
Definition: action.h:203
@ ACTION_LOOT
Sort out the loot.
Definition: action.h:123
@ ACTION_TOGGLE_FULLSCREEN
Toggle full-screen mode.
Definition: action.h:275
@ ACTION_MAP
Display over-map.
Definition: action.h:235
@ ACTION_MEND
Open the mending menu (e.g.
Definition: action.h:163
@ ACTION_TOGGLE_THIEF_MODE
Toggle permanent attitude to stealing.
Definition: action.h:215
@ ACTION_USE_WIELDED
Use currently wielded item.
Definition: action.h:139
@ ACTION_PL_INFO
Display player status screen.
Definition: action.h:233
@ ACTION_DISPLAY_SCENT_TYPE
Toggle scent type map.
Definition: action.h:285
@ ACTION_TOGGLE_AUTO_FORAGING
Turn auto foraging on/off.
Definition: action.h:311
@ ACTION_FIRE_BURST
Burst-fire the current weapon.
Definition: action.h:169
@ ACTION_BIONICS
Open the bionics menu.
Definition: action.h:181
@ ACTION_CONTROL_VEHICLE
Open vehicle control menu.
Definition: action.h:207
@ ACTION_SAVE
Save the game and quit.
Definition: action.h:221
@ ACTION_MOVE_UP
Ascend a staircase.
Definition: action.h:55
@ ACTION_TOGGLE_PANEL_ADM
Turn admin panel on/off.
Definition: action.h:299
@ ACTION_TOGGLE_AUTO_PULP_BUTCHER
Change auto pulp/butcher mode.
Definition: action.h:307
@ ACTION_TOGGLE_AUTO_TRAVEL_MODE
Turn auto travel mode on/off.
Definition: action.h:209
@ ACTION_COLOR
Open color manager.
Definition: action.h:265
@ ACTION_TIMEOUT
Input timeout.
Definition: action.h:35
@ ACTION_TOGGLE_RUN
Toggle run on/off.
Definition: action.h:61
@ ACTION_FACTIONS
Display factions screen.
Definition: action.h:243
@ ACTION_GRAB
Grab or let go of an object.
Definition: action.h:107
@ ACTION_MOVE_BACK
Move towards bottom of screen / decelerate.
Definition: action.h:45
@ ACTION_CAST_SPELL
Cast a spell (only if any spells are known)
Definition: action.h:175
@ ACTION_DIR_DROP
Drop items in a given direction.
Definition: action.h:179
@ ACTION_AUTOATTACK
Auto select and attack hostile creature within range.
Definition: action.h:187
@ ACTION_CYCLE_MOVE
Cycle run/walk/crouch mode.
Definition: action.h:57
@ ACTION_SKY
Show sky state for trying to predict weather.
Definition: action.h:237
@ ACTION_LUA_CONSOLE
Open Lua console.
Definition: action.h:279
@ ACTION_FIRE
Fire the wielded weapon, or open fire menu if none.
Definition: action.h:167
@ ACTION_PAUSE
Pause an on-going activity.
Definition: action.h:33
@ ACTION_MOVE_BACK_RIGHT
Move towards bottom-right of screen / decelerate and steer right.
Definition: action.h:43
@ ACTION_MUTATIONS
Open the mutations menu.
Definition: action.h:183
@ ACTION_HAUL
Haul pile of items, or let go of them.
Definition: action.h:109
@ ACTION_MOVE_RIGHT
Move / steer right.
Definition: action.h:41
@ ACTION_SLEEP
Open sleep menu.
Definition: action.h:205
@ ACTION_ITEMACTION
Open the item uses menu.
Definition: action.h:295
@ ACTION_MOVE_LEFT
Move / steer left.
Definition: action.h:49
@ ACTION_SELECT_DEFAULT_AMMO
Change default ammo for current weapon.
Definition: action.h:173
@ ACTION_AUTOPICKUP
Open autopickup manager.
Definition: action.h:259
@ ACTION_SUICIDE
Commit suicide.
Definition: action.h:227
@ NUM_ACTIONS
Not an action, serves as count of enumerated actions.
Definition: action.h:331
@ ACTION_ZOOM_OUT
Zoom view in.
Definition: action.h:289
@ ACTION_SELECT_FIRE_MODE
Change fire mode of the current weapon.
Definition: action.h:171
@ ACTION_UNLOAD
Open the unload item (e.g.
Definition: action.h:161
@ ACTION_RECRAFT
Repeat last craft command.
Definition: action.h:197
@ ACTION_TAKE_OFF
Open the take-off clothing selection menu.
Definition: action.h:143
@ ACTION_PICKUP_FEET
Pick up items from current square.
Definition: action.h:105
@ ACTION_TOGGLE_AUTO_FEATURES
Turn auto features on/off.
Definition: action.h:305
@ ACTION_WORLD_MODS
Open active world mods.
Definition: action.h:267
@ ACTION_TOGGLE_DEBUG_MODE
Toggle debug mode.
Definition: action.h:287
@ ACTION_ORGANIZE
Swap inventory letters.
Definition: action.h:135
@ ACTION_MOVE_FORTH_LEFT
Move towards top-left of screen / accelerate and steer left.
Definition: action.h:51
@ ACTION_RELOAD_TILESET
Reload current tileset.
Definition: action.h:303
@ ACTION_CLOSE
Close an item (e.g.
Definition: action.h:97
@ ACTION_RELOAD_WEAPON
Attempt to reload wielded weapon, then fall back to the load item select menu.
Definition: action.h:157
@ ACTION_RELOAD_ITEM
Open the load item (e.g.
Definition: action.h:155
@ ACTION_PICKUP
Pick up items from current/adjacent squares.
Definition: action.h:103
@ ACTION_LONGCRAFT
Open batch crafting menu.
Definition: action.h:199
@ ACTION_DISTRACTION_MANAGER
Open distraction manager.
Definition: action.h:269
@ ACTION_WEAR
Open the wear clothing selection menu.
Definition: action.h:141
@ ACTION_DIARY
Display diary window.
Definition: action.h:253
void create_advanced_inv()
void show_armor_layers_ui(Character &who)
auto_notes::auto_note_settings & get_auto_notes_settings()
Definition: auto_note.cpp:386
auto_pickup::player_settings & get_auto_pickup()
Definition: auto_pickup.cpp:38
void show_bionics_ui(Character &who)
Definition: bionics_ui.cpp:537
const bodypart_str_id body_part_head("head")
bool tile_iso
Using isometric tileset.
bool debug_mode
Extended debugging mode, can be toggled during game.
bool has_active_mutation(const trait_id &b) const
Definition: mutation.cpp:365
pimpl< character_martial_arts > martial_arts_data
Definition: character.h:1588
bool has_active_item(const itype_id &id) const
Whether the player carries an active item of the given item type.
Definition: character.cpp:2510
void place_corpse()
std::set< tripoint > get_path_avoid() const override
Returns a set of points we do not want to path through.
Definition: character.cpp:9957
bool has_destination_activity() const
bool is_auto_moving() const
void start_destination_activity()
action_id get_next_auto_move_direction()
item & primary_weapon()
Legacy code hack, don't use.
Definition: melee.cpp:167
const pathfinding_settings & get_pathfinding_settings() const override
Returns settings for pathfinding.
Definition: character.cpp:9971
bool is_armed() const
Returns true if the character is wielding something.
Definition: melee.cpp:206
void dismount()
Definition: character.cpp:1187
void set_value(const std::string &key, const std::string &value)
Definition: creature.cpp:1372
std::string get_value(const std::string &key) const
Definition: creature.cpp:1382
void mod_moves(int nmoves)
Definition: creature.cpp:1449
void cycle_move_mode()
Definition: avatar.cpp:1188
void toggle_map_memory()
Definition: avatar.cpp:123
void toggle_crouch_mode()
Definition: avatar.cpp:1172
void toggle_run_mode()
Definition: avatar.cpp:1163
void disp_morale()
Provides the window and detailed morale data.
Definition: avatar.cpp:1002
void reset_move_mode()
Definition: avatar.cpp:1181
static void show_diary_ui(diary *c_diary)
Definition: diary_ui.cpp:164
void item_action_menu()
void display_radiation()
Definition: game.cpp:11303
void list_missions()
Definition: mission_ui.cpp:22
input_context get_player_input(std::string &action)
bool try_get_left_click_action(action_id &act, const tripoint &mouse_target)
Definition: game.cpp:2295
void set_safe_mode(safe_mode_type mode)
Definition: game.cpp:8652
void reload_tileset(std::function< void(std::string)> out)
Definition: game.cpp:431
void pickup_feet()
Definition: game.cpp:5652
void zones_manager()
Definition: game.cpp:6125
int turnssincelastmon
Definition: game.h:1020
void display_visibility()
Definition: game.cpp:11217
void display_scent()
Definition: game.cpp:11182
bool save()
Returns false if saving failed.
Definition: game.cpp:2747
void butcher()
Definition: game.cpp:8334
void display_temperature()
Definition: game.cpp:11203
bool auto_travel_mode
Definition: game.h:1017
void zoom_out()
Definition: game.cpp:7075
void toggle_pixel_minimap()
Definition: game.cpp:420
void toggle_debug_hour_timer()
Definition: game.cpp:11249
void display_transparency()
Definition: game.cpp:11310
void list_items_monsters()
Definition: game.cpp:7253
void chat()
Definition: npctalk.cpp:397
void quickload()
Definition: game.cpp:11345
void pickup()
Definition: game.cpp:5630
void vertical_move(int z, bool force, bool peeking=false)
Moves the player vertically.
Definition: game.cpp:10015
void open_consume_item_menu()
void display_lighting()
Definition: game.cpp:11277
void control_vehicle()
Definition: game.cpp:5184
void peek()
Definition: game.cpp:5659
void drop()
Definition: game.cpp:8072
bool try_get_right_click_action(action_id &act, const tripoint &mouse_target)
Definition: game.cpp:2323
bool check_safe_mode_allowed(bool repeat_safe_mode_warnings=true)
Check whether movement is allowed according to safe mode settings.
Definition: game.cpp:8590
void zoom_in()
Definition: game.cpp:7087
void toggle_fullscreen()
Definition: game.cpp:410
void display_vehicle_ai()
Definition: game.cpp:11210
void mark_main_ui_adaptor_resize() const
Definition: game.cpp:2998
void drop_in_direction()
Definition: game.cpp:8077
void display_help()
Definition: help.cpp:140
input_event get_raw_input()
Temporary method to retrieve the raw input received, so that input_contexts can be used in screens wh...
Definition: input.cpp:1293
action_id display_menu(bool permit_execute_action=false)
Displays the possible actions in the current context and their keybindings.
Definition: input.cpp:993
std::optional< tripoint > get_coordinates(const catacurses::window &capture_win_)
Get the coordinates associated with the last mouse click (if any).
Definition: input.cpp:1332
std::string get_keyname(int ch, input_event_t inp_type, bool portable=false) const
Get the key name associated with the given keyboard keycode.
Definition: input.cpp:410
bool is_gun() const
Can this item be used to perform a ranged attack?
Definition: item.cpp:6543
void gun_cycle_mode()
Switch to the next available firing mode.
Definition: item.cpp:7937
std::string display_name(unsigned int quantity=1) const
Returns the item name and the charges or contained charges (if the item can have charges at all).
Definition: item.cpp:4846
bool is_gunmod() const
Definition: item.cpp:6573
std::map< gun_mode_id, gun_mode > gun_all_modes() const
Get all possible modes for this gun inclusive of any attached gunmods.
Definition: item.cpp:7856
bool gun_set_mode(const gun_mode_id &mode)
Try to set the mode for a gun, returning false if no such mode is possible.
Definition: item.cpp:7928
bool is_outside(const tripoint &p) const
Definition: map.cpp:2626
std::vector< tripoint > route(const tripoint &f, const tripoint &t, const pathfinding_settings &settings, const std::set< tripoint > &pre_closed={{ }}) const
Calculate the best path using A*.
const tripoint & pos() const override
Definition: monster.cpp:252
short ignoring
Definition: monster.h:505
cOpt & get_option(const std::string &name)
Definition: options.cpp:3396
std::string show(bool ingame=false, bool world_options_only=false, const std::function< bool()> &on_quit=nullptr)
Definition: options.cpp:2773
void show_adm()
Definition: panels.cpp:2299
void craft(const tripoint &loc=tripoint_zero)
Start various types of crafts.
Definition: crafting.cpp:342
int movecounter
Definition: player.h:247
void recraft(const tripoint &loc=tripoint_zero)
Definition: crafting.cpp:353
void long_craft(const tripoint &loc=tripoint_zero)
Definition: crafting.cpp:362
void add_rule(const std::string &rule_in, Creature::Attitude attitude_in, int proximity_in, rule_state state_in)
void show()
Definition: safemode_ui.cpp:39
int moves_elapsed()
#define all_colors
Definition: color.h:15
std::optional< construction_id > construction_menu(const bool blueprint)
@ Info
Information (default: enabled).
@ Main
Generic messages related to game startup and operation.
#define DebugLog(lev, cl)
DebugLog.
Definition: debug.h:285
@ RULE_WHITELISTED
Definition: enums.h:53
@ SAFE_MODE_OFF
Definition: game.h:77
@ QUIT_SAVED
Definition: game.h:70
static void open_movement_mode_menu()
static void smash()
static void open()
static void rcdrive(point d)
#define dbg(x)
static void takeoff()
static void read()
static void wait()
static const efftype_id effect_laserlocked("laserlocked")
static void wear()
static void close()
static const bionic_id bio_remote("bio_remote")
static void pldrive(const tripoint &p)
static void haul()
static const trait_id trait_SHELL2("SHELL2")
static const trait_id trait_PROF_CHURL("PROF_CHURL")
static void cast_spell()
static void loot()
static void fire()
static void grab()
static const itype_id itype_radiocontrol("radiocontrol")
help & get_help()
Definition: help.cpp:30
void show_mutations_ui(Character &who)
bool isDebugger()
Definition: mapsharing.cpp:65
bool isCompetitive()
Definition: mapsharing.cpp:35
void reload_wielded(bool prompt=false)
Reload wielded item.
void reload_item()
Prompt to reload some item.
void use_item(avatar &you, item_location &loc)
bool eat_here(avatar &you)
void wield()
Prompt to wield some item.
void plthrow(avatar &you, item_location loc, const std::optional< tripoint > &blind_throw_from_pos=std::nullopt)
void autoattack(avatar &you, map &m)
void eat(avatar &you)
Eat food or fuel 'E' (or 'a')
void fire_wielded_weapon(avatar &you)
Checks if the wielded weapon is a gun and can be fired then starts interactive aiming.
void reload_weapon(bool try_everything=true)
Reload a wielded gun/tool.
void mend(avatar &you, item_location loc)
void unload(avatar &you)
Prompts to unload some item.
void use_item(avatar &you, item_location loc)
Use a tool at given location.
void show_lua_console()
Definition: catalua.cpp:41
void reload_lua_code()
Definition: catalua.cpp:50
void disp_info(Character &ch)
Handles and displays detailed character info for the '@' screen.
void do_pause(Character &who)
Do pause action ('.
void debug()
void close_door(map &m, Character &who, const tripoint &closep)
Handles deducting moves, printing messages (only non-NPCs cause messages), actually closing it,...
Definition: gates.cpp:257
void common(avatar &you)
void compare(player &p, const std::optional< tripoint > &offset)
void swap_letters(player &p)
void prompt_select_default_ammo_for(avatar &u, const item &w)
Prompts to select default ammo compatible with provided gun.
Definition: ranged.cpp:3805
void display_visible_weather()
Display overmap like with display() and display the weather that is within line of sight.
void display()
Display overmap centered at the player's position.
options_manager & get_options()
Definition: options.cpp:146
T get_option(const std::string &name)
Definition: options.h:368
static constexpr point point_south_west
Definition: point.h:267
static constexpr point point_north_east
Definition: point.h:263
static constexpr point point_north_west
Definition: point.h:269
@ sleep
Will recharge only when character is asleep.
An instance of an input, like a keypress etc.
Definition: input.h:91
std::vector< int > sequence
Definition: input.h:97
int get_first_input() const
Definition: input.cpp:100
input_event_t type
Definition: input.h:92
void handbrake()

References _, Creature::A_ANY, achievements_tracker_ptr, act, action, ACTION_ACTIONMENU, ACTION_ADVANCEDINV, ACTION_AUTOATTACK, ACTION_AUTONOTES, ACTION_AUTOPICKUP, ACTION_BIONICS, ACTION_BUTCHER, ACTION_CAST_SPELL, ACTION_CENTER, ACTION_CHAT, ACTION_CLOSE, ACTION_COLOR, ACTION_COMPARE, ACTION_CONSTRUCT, ACTION_CONTROL_VEHICLE, ACTION_CRAFT, ACTION_CYCLE_MOVE, ACTION_DEBUG, ACTION_DIARY, ACTION_DIR_DROP, ACTION_DISASSEMBLE, ACTION_DISPLAY_LIGHTING, ACTION_DISPLAY_RADIATION, ACTION_DISPLAY_SCENT, ACTION_DISPLAY_SCENT_TYPE, ACTION_DISPLAY_SUBMAP_GRID, ACTION_DISPLAY_TEMPERATURE, ACTION_DISPLAY_TRANSPARENCY, ACTION_DISPLAY_VEHICLE_AI, ACTION_DISPLAY_VISIBILITY, ACTION_DISTRACTION_MANAGER, ACTION_DROP, ACTION_EAT, ACTION_EXAMINE, ACTION_FACTIONS, ACTION_FIRE, ACTION_FIRE_BURST, ACTION_GRAB, ACTION_HAUL, ACTION_HELP, action_ident(), ACTION_IGNORE_ENEMY, ACTION_INVENTORY, ACTION_ITEMACTION, ACTION_KEYBINDINGS, ACTION_LIST_ITEMS, ACTION_LONGCRAFT, ACTION_LOOK, ACTION_LOOT, ACTION_LUA_CONSOLE, ACTION_LUA_RELOAD, ACTION_MAIN_MENU, ACTION_MAP, ACTION_MEND, ACTION_MESSAGES, ACTION_MISSIONS, ACTION_MORALE, ACTION_MOVE_BACK, ACTION_MOVE_BACK_LEFT, ACTION_MOVE_BACK_RIGHT, ACTION_MOVE_DOWN, ACTION_MOVE_FORTH, ACTION_MOVE_FORTH_LEFT, ACTION_MOVE_FORTH_RIGHT, ACTION_MOVE_LEFT, ACTION_MOVE_RIGHT, ACTION_MOVE_UP, ACTION_MUTATIONS, ACTION_NULL, ACTION_OPEN, ACTION_OPEN_CONSUME, ACTION_OPEN_MOVEMENT, ACTION_OPTIONS, ACTION_ORGANIZE, ACTION_PAUSE, ACTION_PEEK, ACTION_PICK_STYLE, ACTION_PICKUP, ACTION_PICKUP_FEET, ACTION_PL_INFO, ACTION_QUICKLOAD, ACTION_QUICKSAVE, ACTION_READ, ACTION_RECRAFT, ACTION_RELOAD_ITEM, ACTION_RELOAD_TILESET, ACTION_RELOAD_WEAPON, ACTION_RELOAD_WIELDED, ACTION_RESET_MOVE, ACTION_SAFEMODE, ACTION_SAVE, ACTION_SCORES, ACTION_SEC_SELECT, ACTION_SELECT, ACTION_SELECT_DEFAULT_AMMO, ACTION_SELECT_FIRE_MODE, ACTION_SHIFT_E, ACTION_SHIFT_N, ACTION_SHIFT_NE, ACTION_SHIFT_NW, ACTION_SHIFT_S, ACTION_SHIFT_SE, ACTION_SHIFT_SW, ACTION_SHIFT_W, ACTION_SKY, ACTION_SLEEP, ACTION_SMASH, ACTION_SORT_ARMOR, ACTION_SUICIDE, ACTION_TAKE_OFF, ACTION_THROW, ACTION_TIMEOUT, ACTION_TOGGLE_AUTO_FEATURES, ACTION_TOGGLE_AUTO_FORAGING, ACTION_TOGGLE_AUTO_MINING, ACTION_TOGGLE_AUTO_PICKUP, ACTION_TOGGLE_AUTO_PULP_BUTCHER, ACTION_TOGGLE_AUTO_TRAVEL_MODE, ACTION_TOGGLE_AUTOSAFE, ACTION_TOGGLE_CROUCH, ACTION_TOGGLE_DEBUG_MODE, ACTION_TOGGLE_FULLSCREEN, ACTION_TOGGLE_HOUR_TIMER, ACTION_TOGGLE_MAP_MEMORY, ACTION_TOGGLE_PANEL_ADM, ACTION_TOGGLE_PIXEL_MINIMAP, ACTION_TOGGLE_RUN, ACTION_TOGGLE_SAFEMODE, ACTION_TOGGLE_THIEF_MODE, ACTION_UNLOAD, ACTION_USE, ACTION_USE_WIELDED, ACTION_WAIT, ACTION_WEAR, ACTION_WHITELIST_ENEMY, ACTION_WIELD, ACTION_WORLD_MODS, ACTION_ZONES, ACTION_ZOOM_IN, ACTION_ZOOM_OUT, add_msg(), safemode::add_rule(), all_colors, Character::apply_damage(), auto_travel_mode, avatar_action::autoattack(), bio_remote, body_part_head, butcher(), can_action_change_worldstate(), cast_spell(), chat(), check_safe_mode_allowed(), Character::clear_destination(), close(), doors::close_door(), game_menus::inv::common(), game_menus::inv::compare(), construction_menu(), control_vehicle(), Character::controlling_vehicle, player::craft(), create_advanced_inv(), avatar::cycle_move_mode(), dbg, debug_menu::debug(), debug_mode, DebugLog, destination_preview, crafting::disassemble(), Character::dismount(), character_display::disp_info(), avatar::disp_morale(), ui::omap::display(), help::display_help(), display_lighting(), input_context::display_menu(), Messages::display_messages(), item::display_name(), display_radiation(), display_scent(), display_temperature(), display_transparency(), display_vehicle_ai(), display_visibility(), ui::omap::display_visible_weather(), character_funcs::do_pause(), driving_view_offset, drop(), drop_in_direction(), avatar_action::eat(), avatar_action::eat_here(), effect_laserlocked, examine(), faction_manager_ptr, fire(), avatar_action::fire_wielded_weapon(), g, gamemode, get_auto_notes_settings(), get_auto_pickup(), avatar::get_avatar_diary(), input_context::get_coordinates(), get_delta_from_movement_action(), get_distraction_manager(), input_event::get_first_input(), get_help(), input_manager::get_keyname(), get_kill_tracker(), panel_manager::get_manager(), avatar::get_mon_visible(), Character::get_next_auto_move_direction(), options_manager::get_option(), get_option(), get_options(), Character::get_path_avoid(), Character::get_pathfinding_settings(), get_player_input(), input_context::get_raw_input(), get_safemode(), Creature::get_value(), grab(), item::gun_all_modes(), item::gun_cycle_mode(), item::gun_set_mode(), handbrake(), handle_action_menu(), handle_main_menu(), Character::has_active_bionic(), Character::has_active_item(), Character::has_active_mutation(), Character::has_destination(), Character::has_destination_activity(), Creature::has_effect(), Character::has_trait(), haul(), monster::ignoring, Character::in_vehicle, Info, inp_mngr, Character::is_armed(), Character::is_auto_moving(), Character::is_dead_state(), item::is_gun(), item::is_gunmod(), Character::is_mounted(), map::is_outside(), MAP_SHARING::isCompetitive(), MAP_SHARING::isDebugger(), item_action_menu(), itype_radiocontrol, list_items_monsters(), list_missions(), player::long_craft(), look_around(), look_up_action(), loot(), m, m_bad, m_info, m_warning, Main, mark_main_ui_adaptor_resize(), Character::martial_arts_data, avatar_action::mend(), MF_RIDEABLE_MECH, Creature::mod_moves(), mostseen, Character::mounted_creature, avatar_action::move(), player::movecounter, Creature::moves, user_turn::moves_elapsed(), om_direction::name(), monster_visible_info::new_seen_mon, no, NUM_ACTIONS, open(), open_consume_item_menu(), open_movement_mode_menu(), peek(), pickup(), pickup_feet(), Character::place_corpse(), pldrive(), avatar_action::plthrow(), point_east, point_north, point_north_east, point_north_west, point_south, point_south_east, point_south_west, point_west, point_zero, Character::pos(), monster::pos(), Character::posx(), Character::posy(), Character::posz(), press_x(), press_x_if_bound(), Character::primary_weapon(), ranged::prompt_select_default_ammo_for(), query_yn(), quickload(), quicksave(), QUIT_DIED, QUIT_SAVED, QUIT_SUICIDE, QUIT_WATCH, rcdrive(), read(), player::recraft(), avatar_action::reload_item(), cata::reload_lua_code(), reload_tileset(), avatar_action::reload_weapon(), avatar_action::reload_wielded(), remoteveh(), Creature::remove_effect(), avatar::reset_move_mode(), rl_dist(), map::route(), RULE_WHITELISTED, safe_mode, SAFE_MODE_OFF, SAFE_MODE_ON, SAFE_MODE_STOP, safe_mode_warning_logged, save(), options_manager::save(), Character::sees(), SEEX, input_event::sequence, Character::set_destination(), set_safe_mode(), Creature::set_value(), options_manager::cOpt::setNext(), auto_pickup::player_settings::show(), distraction_manager::distraction_manager_gui::show(), safemode::show(), options_manager::show(), panel_manager::show_adm(), show_armor_layers_ui(), show_bionics_ui(), diary::show_diary_ui(), auto_notes::auto_note_settings::show_gui(), cata::show_lua_console(), show_mutations_ui(), show_scores_ui(), sleep, smash(), Character::start_destination_activity(), stats(), string_format(), game_menus::inv::swap_letters(), takeoff(), tile_iso, avatar::toggle_crouch_mode(), toggle_debug_hour_timer(), toggle_fullscreen(), avatar::toggle_map_memory(), toggle_pixel_minimap(), avatar::toggle_run_mode(), trait_PROF_CHURL, trait_SHELL2, tripoint_above, tripoint_below, try_get_left_click_action(), try_get_right_click_action(), calendar::turn, turnssincelastmon, input_event::type, u, avatar_action::unload(), uquit, avatar_action::use_item(), avatar_funcs::use_item(), use_tiles, user_action_counter, map::veh_at(), vertical_move(), player::view_offset, w_terrain, wait(), wear(), avatar_action::wield(), world_generator, point::x, tripoint::x, point::y, tripoint::y, yes, zones_manager(), zoom_in(), and zoom_out().

Referenced by do_turn().

◆ handle_key_blocking_activity()

void game::handle_key_blocking_activity ( )
private

Definition at line 1972 of file game.cpp.

1973{
1975 const std::string action = ctxt.handle_input( 0 );
1976 bool refresh = true;
1977 if( action == "pause" || action == "main_menu" ) {
1979 cancel_activity_query( _( "Confirm:" ) );
1980 }
1981 } else if( action == "player_data" ) {
1983 } else if( action == "messages" ) {
1985 } else if( action == "help" ) {
1987 } else if( action != "HELP_KEYBINDINGS" ) {
1988 refresh = false;
1989 }
1990 if( refresh ) {
1993 }
1994}
bool cancel_activity_query(const std::string &text)
Asks if the player wants to cancel their activity, and if so cancels it.
Definition: game.cpp:1756
const std::string & handle_input()
Handles input and returns the next action in the queue.
Definition: input.cpp:848
bool interruptable_with_kb
Controls whether this activity can be cancelled with 'pause' action.
void refresh()

References _, action, Character::activity, cancel_activity_query(), character_display::disp_info(), help::display_help(), Messages::display_messages(), get_default_mode_input_context(), get_help(), input_context::handle_input(), player_activity::interruptable_with_kb, ui_manager::redraw(), catacurses::refresh(), refresh_display(), and u.

Referenced by process_voluntary_act_interrupt().

◆ handle_mouseview()

bool game::handle_mouseview ( input_context ctxt,
std::string &  action 
)
private

Definition at line 1998 of file game.cpp.

1999{
2000 std::optional<tripoint> liveview_pos;
2001
2002 do {
2003 action = ctxt.handle_input();
2004 if( action == "MOUSE_MOVE" ) {
2005 const std::optional<tripoint> mouse_pos = ctxt.get_coordinates( w_terrain );
2006 if( mouse_pos && ( !liveview_pos || *mouse_pos != *liveview_pos ) ) {
2007 liveview_pos = mouse_pos;
2008 liveview.show( *liveview_pos );
2009 } else if( !mouse_pos ) {
2010 liveview_pos.reset();
2011 liveview.hide();
2012 }
2014 }
2015 } while( action == "MOUSE_MOVE" ); // Freeze animation when moving the mouse
2016
2017 if( action != "TIMEOUT" ) {
2018 // Keyboard event, break out of animation loop
2019 liveview.hide();
2020 return false;
2021 }
2022
2023 // Mouse movement or un-handled key
2024 return true;
2025}
void hide()
Definition: live_view.cpp:33
void show(const tripoint &p)
Definition: live_view.cpp:38

References action, input_context::get_coordinates(), input_context::handle_input(), live_view::hide(), liveview, ui_manager::redraw(), live_view::show(), and w_terrain.

Referenced by get_player_input().

◆ has_gametype()

bool game::has_gametype ( ) const

Definition at line 534 of file game.cpp.

535{
536 return gamemode && gamemode->id() != special_game_type::NONE;
537}

References gamemode, and NONE.

◆ init_autosave()

void game::init_autosave ( )
private

Definition at line 11317 of file game.cpp.

11318{
11320 last_save_timestamp = time( nullptr );
11321}

References last_save_timestamp, moves_since_last_save, and time.

Referenced by load(), and start_game().

◆ inv_map_splice()

item_location game::inv_map_splice ( item_filter  filter,
const std::string &  title,
int  radius = 0,
const std::string &  none_message = "" 
)

Custom-filtered menu for inventory and nearby items and those that within specified radius.

Definition at line 400 of file game_inventory.cpp.

402{
404 title, radius, none_message );
405}
static item_location_filter convert_filter(const item_filter &filter)
static item_location inv_internal(player &u, const inventory_selector_preset &preset, const std::string &title, int radius, const std::string &none_message, const std::string &hint=std::string())
std::string title(holiday current_holiday)
Definition: path_info.cpp:330

References convert_filter(), inv_internal(), PATH_INFO::title(), and u.

◆ invalidate_main_ui_adaptor()

void game::invalidate_main_ui_adaptor ( ) const

◆ is_dangerous_tile()

bool game::is_dangerous_tile ( const tripoint dest_loc) const

Definition at line 8720 of file game.cpp.

8721{
8722 return !( get_dangerous_tile( dest_loc ).empty() );
8723}
std::vector< std::string > get_dangerous_tile(const tripoint &dest_loc) const
Definition: game.cpp:8748

References get_dangerous_tile().

Referenced by walk_move().

◆ is_empty()

bool game::is_empty ( const tripoint p)

Returns true if there is no player, NPC, or monster on the tile and move_cost > 0.

Definition at line 4849 of file game.cpp.

4850{
4851 return ( m.passable( p ) || m.has_flag( "LIQUID", p ) ) &&
4852 critter_at( p ) == nullptr;
4853}

References critter_at(), map::has_flag(), m, and map::passable().

Referenced by grabbed_furn_move(), monmove(), place_player(), and update_stair_monsters().

◆ is_game_over()

bool game::is_game_over ( )
private

Definition at line 2368 of file game.cpp.

2369{
2370 if( uquit == QUIT_WATCH ) {
2371 // deny player movement and dodging
2372 u.moves = 0;
2373 // prevent pain from updating
2374 u.set_pain( 0 );
2375 // prevent dodging
2376 u.dodges_left = 0;
2377 return false;
2378 }
2379 if( uquit == QUIT_DIED ) {
2380 if( u.in_vehicle ) {
2381 m.unboard_vehicle( u.pos() );
2382 }
2383 u.place_corpse();
2384 return true;
2385 }
2386 if( uquit == QUIT_SUICIDE ) {
2387 if( u.in_vehicle ) {
2388 m.unboard_vehicle( u.pos() );
2389 }
2390 return true;
2391 }
2392 if( uquit != QUIT_NO ) {
2393 return true;
2394 }
2395 // is_dead_state() already checks hp_torso && hp_head, no need to for loop it
2396 if( u.is_dead_state() ) {
2397 if( get_option<bool>( "PROMPT_ON_CHARACTER_DEATH" ) &&
2398 !query_yn(
2399 _( "Your character is dead, do you accept this?\n\nSelect Yes to abandon the character to their fate, select No to return to main menu." ) ) ) {
2400 return true;
2401 }
2402
2404 if( get_option<std::string>( "DEATHCAM" ) == "always" ) {
2405 uquit = QUIT_WATCH;
2406 } else if( get_option<std::string>( "DEATHCAM" ) == "ask" ) {
2407 uquit = query_yn( _( "Watch the last moments of your life…?" ) ) ?
2409 } else if( get_option<std::string>( "DEATHCAM" ) == "never" ) {
2410 uquit = QUIT_DIED;
2411 } else {
2412 // Something funky happened here, just die.
2413 dbg( DL::Error ) << "no deathcam option given to options, defaulting to QUIT_DIED";
2414 uquit = QUIT_DIED;
2415 }
2416 return is_game_over();
2417 }
2418 return false;
2419}
int dodges_left
Definition: character.h:569
void set_pain(int npain) override
Sets new intensity of pain an reacts to it.
Definition: character.cpp:792
@ Error
Error (default: enabled).
#define dbg(x)
Definition: game.cpp:200
void deactivate()
Definition: messages.cpp:357

References _, dbg, Messages::deactivate(), Character::dodges_left, Error, Character::in_vehicle, Character::is_dead_state(), is_game_over(), m, Creature::moves, Character::place_corpse(), Character::pos(), query_yn(), QUIT_DIED, QUIT_NO, QUIT_SUICIDE, QUIT_WATCH, Character::set_pain(), u, map::unboard_vehicle(), and uquit.

Referenced by do_turn(), and is_game_over().

◆ is_hostile_nearby()

Creature * game::is_hostile_nearby ( )

Definition at line 3589 of file game.cpp.

3590{
3591 int distance = ( get_option<int>( "SAFEMODEPROXIMITY" ) <= 0 ) ? MAX_VIEW_DISTANCE :
3592 get_option<int>( "SAFEMODEPROXIMITY" );
3593 return is_hostile_within( distance );
3594}
Creature * is_hostile_within(int distance)
Definition: game.cpp:3601

References is_hostile_within(), and MAX_VIEW_DISTANCE.

◆ is_hostile_very_close()

Creature * game::is_hostile_very_close ( )

Definition at line 3596 of file game.cpp.

3597{
3599}
static constexpr int DANGEROUS_PROXIMITY
Definition: game.cpp:202

References DANGEROUS_PROXIMITY, and is_hostile_within().

Referenced by butcher(), and process_voluntary_act_interrupt().

◆ is_hostile_within()

Creature * game::is_hostile_within ( int  distance)
private

Definition at line 3601 of file game.cpp.

3602{
3603 for( auto &critter : u.get_visible_creatures( distance ) ) {
3604 if( u.attitude_to( *critter ) == Creature::A_HOSTILE ) {
3605 return critter;
3606 }
3607 }
3608
3609 return nullptr;
3610}
Attitude attitude_to(const Creature &other) const override
Attitude (of this creature) towards another creature.
std::vector< Creature * > get_visible_creatures(int range) const
Returns all creatures that this player can see and that are in the given range.
@ A_HOSTILE
Definition: creature.h:167

References Creature::A_HOSTILE, Character::attitude_to(), Character::get_visible_creatures(), and u.

Referenced by is_hostile_nearby(), and is_hostile_very_close().

◆ is_in_sunlight()

bool game::is_in_sunlight ( const tripoint p)

Returns true if p is outdoors and it is sunny.

Definition at line 4855 of file game.cpp.

4856{
4857 return weather::is_in_sunlight( m, p, get_weather().weather_id );
4858}
bool is_in_sunlight(const map &m, const tripoint &p, const weather_type_id &weather)
Definition: weather.cpp:1162

References get_weather, weather::is_in_sunlight(), and m.

Referenced by process_artifact().

◆ is_in_viewport()

bool game::is_in_viewport ( const tripoint p,
int  margin = 0 
) const

Definition at line 3235 of file game.cpp.

3236{
3237 const tripoint diff( u.pos() + u.view_offset - p );
3238
3239 return ( std::abs( diff.x ) <= getmaxx( w_terrain ) / 2 - margin ) &&
3240 ( std::abs( diff.y ) <= getmaxy( w_terrain ) / 2 - margin );
3241}

References catacurses::getmaxx(), catacurses::getmaxy(), Character::pos(), u, player::view_offset, w_terrain, tripoint::x, and tripoint::y.

◆ is_sheltered()

bool game::is_sheltered ( const tripoint p)

Returns true if p is indoors, underground, or in a car.

Definition at line 4860 of file game.cpp.

4861{
4862 return weather::is_sheltered( m, p );
4863}
bool is_sheltered(const map &m, const tripoint &p)
Definition: weather.cpp:1153

References weather::is_sheltered(), and m.

◆ is_zones_manager_open()

bool game::is_zones_manager_open ( ) const

Definition at line 6055 of file game.cpp.

6056{
6057 return zones_manager_open;
6058}
bool zones_manager_open
Is Zone manager open or not - changes graphics of some zone tiles.
Definition: game.h:1052

References zones_manager_open.

◆ item_action_menu()

void game::item_action_menu ( )
private

Definition at line 231 of file item_action.cpp.

232{
233 const auto &gen = item_action_generator::generator();
234 const action_map &item_actions = gen.get_item_action_map();
235
236 // HACK: A bit of a hack for now. If more pseudos get implemented, this should be un-hacked
237 std::vector<item *> pseudos;
238 item toolset( "toolset", calendar::turn );
239 if( u.has_active_bionic( bio_tools ) ) {
240 pseudos.push_back( &toolset );
241 }
242 item bio_claws_item( static_cast<std::string>( bio_claws_weapon ), calendar::turn );
243 if( u.has_active_bionic( bio_claws ) ) {
244 pseudos.push_back( &bio_claws_item );
245 }
246
247 item_action_map iactions = gen.map_actions_to_items( u, pseudos );
248 if( iactions.empty() ) {
249 popup( _( "You don't have any items with registered uses" ) );
250 }
251
252 uilist kmenu;
253 kmenu.text = _( "Execute which action?" );
254 kmenu.input_category = "ITEM_ACTIONS";
255 input_context ctxt( "ITEM_ACTIONS" );
256 for( const auto &id : item_actions ) {
257 ctxt.register_action( id.first, id.second.name );
258 kmenu.additional_actions.emplace_back( id.first, id.second.name );
259 }
260 actmenu_cb callback( item_actions );
261 kmenu.callback = &callback;
262 int num = 0;
263
264 const auto assigned_action = [&iactions]( const item_action_id & action ) {
265 return iactions.find( action ) != iactions.end();
266 };
267
268 std::vector<std::tuple<item_action_id, std::string, std::string>> menu_items;
269 // Sorts menu items by action.
270 using Iter = decltype( menu_items )::iterator;
271 const auto sort_menu = []( Iter from, Iter to ) {
272 std::sort( from, to, []( const std::tuple<item_action_id, std::string, std::string> &lhs,
273 const std::tuple<item_action_id, std::string, std::string> &rhs ) {
274 return std::get<1>( lhs ).compare( std::get<1>( rhs ) ) < 0;
275 } );
276 };
277 // Add mapped actions to the menu vector.
278 std::transform( iactions.begin(), iactions.end(), std::back_inserter( menu_items ),
279 []( const std::pair<item_action_id, item *> &elem ) {
280 std::string ss = elem.second->display_name();
281 if( elem.second->ammo_required() ) {
282 ss += string_format( " (%d/%d)", elem.second->ammo_required(), elem.second->ammo_remaining() );
283 }
284
285 const auto method = elem.second->get_use( elem.first );
286 if( method ) {
287 return std::make_tuple( method->get_type(), method->get_name(), ss );
288 } else {
289 return std::make_tuple( errstring, std::string( "NO USE FUNCTION" ), ss );
290 }
291 } );
292 // Sort mapped actions.
293 sort_menu( menu_items.begin(), menu_items.end() );
294 // Add unmapped but binded actions to the menu vector.
295 for( const auto &elem : item_actions ) {
296 if( key_bound_to( ctxt, elem.first ) != '\0' && !assigned_action( elem.first ) ) {
297 menu_items.emplace_back( elem.first, gen.get_action_name( elem.first ), "-" );
298 }
299 }
300 // Sort unmapped actions.
301 auto iter = menu_items.begin();
302 std::advance( iter, iactions.size() );
303 sort_menu( iter, menu_items.end() );
304 // Determine max lengths, to print the menu nicely.
305 std::pair<int, int> max_len;
306 for( const auto &elem : menu_items ) {
307 max_len.first = std::max( max_len.first, utf8_width( std::get<1>( elem ), true ) );
308 max_len.second = std::max( max_len.second, utf8_width( std::get<2>( elem ), true ) );
309 }
310 // Fill the menu.
311 for( const auto &elem : menu_items ) {
312 std::string ss;
313 ss += std::get<1>( elem );
314 ss += std::string( max_len.first - utf8_width( std::get<1>( elem ), true ), ' ' );
315 ss += std::string( 4, ' ' );
316
317 ss += std::get<2>( elem );
318 ss += std::string( max_len.second - utf8_width( std::get<2>( elem ), true ), ' ' );
319
320 const char bind = key_bound_to( ctxt, std::get<0>( elem ) );
321 const bool enabled = assigned_action( std::get<0>( elem ) );
322
323 kmenu.addentry( num, enabled, bind, ss );
324 num++;
325 }
326
327 kmenu.query();
328 if( kmenu.ret < 0 || kmenu.ret >= static_cast<int>( iactions.size() ) ) {
329 return;
330 }
331
332 const item_action_id action = std::get<0>( menu_items[kmenu.ret] );
333 item *it = iactions[action];
334
335 u.invoke_item( it, action );
336
337 u.inv.restack( u );
338 u.inv.unsort();
339}
inventory inv
Definition: character.h:1581
bool invoke_item(item *, const tripoint &pt) override
Asks how to use the item (if it has more than one use_method) and uses it.
Definition: avatar.cpp:1257
void restack(player &p)
Definition: inventory.cpp:400
void unsort()
Definition: inventory.cpp:228
static item_action_generator & generator()
Definition: item_action.h:32
std::string input_category
Definition: ui.h:325
std::vector< std::pair< std::string, translation > > additional_actions
Definition: ui.h:326
static char key_bound_to(const input_context &ctxt, const item_action_id &act)
Definition: item_action.cpp:47
static const bionic_id bio_claws("bio_claws")
static const bionic_id bio_tools("bio_tools")
static const bionic_id bio_claws_weapon("bio_claws_weapon")
std::string item_action_id
Definition: item_action.h:16
std::map< item_action_id, item_action > action_map
Definition: item_action.h:18
std::map< item_action_id, item * > item_action_map
Definition: item_action.h:17

References _, action, uilist::additional_actions, bio_claws, bio_claws_weapon, bio_tools, uilist::callback, item_action_generator::generator(), Character::has_active_bionic(), uilist::input_category, num, popup(), input_context::register_action(), second, uilist::text, iexamine::transform(), calendar::turn, and u.

Referenced by handle_action().

◆ knockback() [1/2]

void game::knockback ( const tripoint s,
const tripoint t,
int  force,
int  stun,
int  dam_mult,
Creature source 
)

Definition at line 4254 of file game.cpp.

4256{
4257 std::vector<tripoint> traj;
4258 traj.clear();
4259 traj = line_to( s, t, 0, 0 );
4260 traj.insert( traj.begin(), s ); // how annoying, line_to() doesn't include the originating point!
4261 traj = continue_line( traj, force );
4262 traj.insert( traj.begin(), t ); // how annoying, continue_line() doesn't either!
4263
4264 knockback( traj, stun, dam_mult, source );
4265}
std::vector< coords::coord_point< Point, Origin, Scale > > line_to(const coords::coord_point< Point, Origin, Scale > &loc1, const coords::coord_point< Point, Origin, Scale > &loc2)
Definition: coordinates.h:548
std::vector< tripoint > continue_line(const std::vector< tripoint > &line, const int distance)
Definition: line.cpp:408

References continue_line(), knockback(), and line_to().

Referenced by forced_door_closing(), and knockback().

◆ knockback() [2/2]

void game::knockback ( std::vector< tripoint > &  traj,
int  stun,
int  dam_mult,
Creature source = nullptr 
)

Definition at line 4271 of file game.cpp.

4273{
4274 // TODO: make the force parameter actually do something.
4275 // the header file says higher force causes more damage.
4276 // perhaps that is what it should do?
4277
4278 // TODO: refactor this so it's not copy/pasted 3 times
4279 tripoint tp = traj.front();
4280 if( !critter_at( tp ) ) {
4281 debugmsg( _( "Nothing at (%d,%d,%d) to knockback!" ), tp.x, tp.y, tp.z );
4282 return;
4283 }
4284 std::size_t force_remaining = traj.size();
4285 if( monster *const targ = critter_at<monster>( tp, true ) ) {
4286 tripoint start_pos = targ->pos();
4287
4288 if( stun > 0 ) {
4289 targ->add_effect( effect_stunned, 1_turns * stun );
4290 add_msg( _( "%s was stunned!" ), targ->name() );
4291 }
4292 for( size_t i = 1; i < traj.size(); i++ ) {
4293 if( m.impassable( traj[i].xy() ) || m.obstructed_by_vehicle_rotation( tp, traj[i] ) ) {
4294 targ->setpos( traj[i - 1] );
4295 force_remaining = traj.size() - i;
4296 if( stun != 0 ) {
4297 targ->add_effect( effect_stunned, 1_turns * force_remaining );
4298 add_msg( _( "%s was stunned!" ), targ->name() );
4299 add_msg( _( "%s slammed into an obstacle!" ), targ->name() );
4300 targ->apply_damage( source, bodypart_id( "torso" ), dam_mult * force_remaining );
4301 targ->check_dead_state();
4302 }
4303 m.bash( traj[i], 2 * dam_mult * force_remaining );
4304 break;
4305 } else if( critter_at( traj[i] ) ) {
4306 targ->setpos( traj[i - 1] );
4307 force_remaining = traj.size() - i;
4308 if( stun != 0 ) {
4309 targ->add_effect( effect_stunned, 1_turns * force_remaining );
4310 add_msg( _( "%s was stunned!" ), targ->name() );
4311 }
4312 traj.erase( traj.begin(), traj.begin() + i );
4313 if( critter_at<monster>( traj.front() ) ) {
4314 add_msg( _( "%s collided with something else and sent it flying!" ),
4315 targ->name() );
4316 } else if( npc *const guy = critter_at<npc>( traj.front() ) ) {
4317 if( guy->male ) {
4318 add_msg( _( "%s collided with someone else and sent him flying!" ),
4319 targ->name() );
4320 } else {
4321 add_msg( _( "%s collided with someone else and sent her flying!" ),
4322 targ->name() );
4323 }
4324 } else if( u.pos() == traj.front() ) {
4325 add_msg( m_bad, _( "%s collided with you and sent you flying!" ), targ->name() );
4326 }
4327 knockback( traj, stun, dam_mult, source );
4328 break;
4329 }
4330 targ->setpos( traj[i] );
4331 if( m.has_flag( "LIQUID", targ->pos() ) && targ->can_drown() && !targ->is_dead() ) {
4332 targ->die( source );
4333 if( u.sees( *targ ) ) {
4334 add_msg( _( "The %s drowns!" ), targ->name() );
4335 }
4336 }
4337 if( !m.has_flag( "LIQUID", targ->pos() ) && targ->has_flag( MF_AQUATIC ) &&
4338 !targ->is_dead() ) {
4339 targ->die( source );
4340 if( u.sees( *targ ) ) {
4341 add_msg( _( "The %s flops around and dies!" ), targ->name() );
4342 }
4343 }
4344 tp = traj[i];
4345 if( start_pos != targ->pos() ) {
4346 map &here = get_map();
4347 here.creature_on_trap( *targ );
4348 }
4349 }
4350 } else if( npc *const targ = critter_at<npc>( tp ) ) {
4351 tripoint start_pos = targ->pos();
4352
4353 if( stun > 0 ) {
4354 targ->add_effect( effect_stunned, 1_turns * stun );
4355 add_msg( _( "%s was stunned!" ), targ->name );
4356 }
4357 for( size_t i = 1; i < traj.size(); i++ ) {
4358 if( m.impassable( traj[i].xy() ) ||
4359 m.obstructed_by_vehicle_rotation( tp, traj[i] ) ) { // oops, we hit a wall!
4360 targ->setpos( traj[i - 1] );
4361 force_remaining = traj.size() - i;
4362 if( stun != 0 ) {
4363 targ->add_effect( effect_stunned, 1_turns * force_remaining );
4364 if( targ->has_effect( effect_stunned ) ) {
4365 add_msg( _( "%s was stunned!" ), targ->name );
4366 }
4367
4368 std::array<bodypart_id, 8> bps = {{
4369 bodypart_id( "head" ),
4370 bodypart_id( "arm_l" ), bodypart_id( "arm_r" ),
4371 bodypart_id( "hand_l" ), bodypart_id( "hand_r" ),
4372 bodypart_id( "torso" ),
4373 bodypart_id( "leg_l" ), bodypart_id( "leg_r" )
4374 }
4375 };
4376 for( const bodypart_id &bp : bps ) {
4377 if( one_in( 2 ) ) {
4378 targ->deal_damage( source, bp, damage_instance( DT_BASH, force_remaining * dam_mult ) );
4379 }
4380 }
4381 targ->check_dead_state();
4382 }
4383 m.bash( traj[i], 2 * dam_mult * force_remaining );
4384 break;
4385 } else if( critter_at( traj[i] ) ) {
4386 targ->setpos( traj[i - 1] );
4387 force_remaining = traj.size() - i;
4388 if( stun != 0 ) {
4389 add_msg( _( "%s was stunned!" ), targ->name );
4390 targ->add_effect( effect_stunned, 1_turns * force_remaining );
4391 }
4392 traj.erase( traj.begin(), traj.begin() + i );
4393 const tripoint &traj_front = traj.front();
4394 if( critter_at<monster>( traj_front ) ) {
4395 add_msg( _( "%s collided with something else and sent it flying!" ),
4396 targ->name );
4397 } else if( npc *const guy = critter_at<npc>( traj_front ) ) {
4398 if( guy->male ) {
4399 add_msg( _( "%s collided with someone else and sent him flying!" ),
4400 targ->name );
4401 } else {
4402 add_msg( _( "%s collided with someone else and sent her flying!" ),
4403 targ->name );
4404 }
4405 } else if( u.posx() == traj_front.x && u.posy() == traj_front.y &&
4407 ( u.footwear_factor() == .5 && one_in( 2 ) ) ) ) ) {
4408 add_msg( _( "%s collided with you, and barely dislodges your tentacles!" ), targ->name );
4409 } else if( u.posx() == traj_front.x && u.posy() == traj_front.y ) {
4410 add_msg( m_bad, _( "%s collided with you and sent you flying!" ), targ->name );
4411 }
4412 knockback( traj, stun, dam_mult, source );
4413 break;
4414 }
4415 targ->setpos( traj[i] );
4416 tp = traj[i];
4417
4418 if( start_pos != targ->pos() ) {
4419 map &here = get_map();
4420 here.creature_on_trap( *targ );
4421 }
4422 }
4423 } else if( u.pos() == tp ) {
4424 tripoint start_pos = u.pos();
4425
4426 if( stun > 0 ) {
4427 u.add_effect( effect_stunned, 1_turns * stun );
4428 add_msg( m_bad, vgettext( "You were stunned for %d turn!",
4429 "You were stunned for %d turns!",
4430 stun ),
4431 stun );
4432 }
4433 for( size_t i = 1; i < traj.size(); i++ ) {
4434 if( m.impassable( traj[i] ) ||
4435 m.obstructed_by_vehicle_rotation( tp, traj[i] ) ) { // oops, we hit a wall!
4436 u.setpos( traj[i - 1] );
4437 force_remaining = traj.size() - i;
4438 if( stun != 0 ) {
4439 if( u.has_effect( effect_stunned ) ) {
4440 add_msg( m_bad, vgettext( "You were stunned AGAIN for %d turn!",
4441 "You were stunned AGAIN for %d turns!",
4442 force_remaining ),
4443 force_remaining );
4444 } else {
4445 add_msg( m_bad, vgettext( "You were stunned for %d turn!",
4446 "You were stunned for %d turns!",
4447 force_remaining ),
4448 force_remaining );
4449 }
4450 u.add_effect( effect_stunned, 1_turns * force_remaining );
4451 std::array<bodypart_id, 8> bps = {{
4452 bodypart_id( "head" ),
4453 bodypart_id( "arm_l" ), bodypart_id( "arm_r" ),
4454 bodypart_id( "hand_l" ), bodypart_id( "hand_r" ),
4455 bodypart_id( "torso" ),
4456 bodypart_id( "leg_l" ), bodypart_id( "leg_r" )
4457 }
4458 };
4459 for( const bodypart_id &bp : bps ) {
4460 if( one_in( 2 ) ) {
4461 u.deal_damage( source, bp, damage_instance( DT_BASH, force_remaining * dam_mult ) );
4462 }
4463 }
4465 }
4466 m.bash( traj[i], 2 * dam_mult * force_remaining );
4467 break;
4468 } else if( critter_at( traj[i] ) ) {
4469 u.setpos( traj[i - 1] );
4470 force_remaining = traj.size() - i;
4471 if( stun != 0 ) {
4472 if( u.has_effect( effect_stunned ) ) {
4473 add_msg( m_bad, vgettext( "You were stunned AGAIN for %d turn!",
4474 "You were stunned AGAIN for %d turns!",
4475 force_remaining ),
4476 force_remaining );
4477 } else {
4478 add_msg( m_bad, vgettext( "You were stunned for %d turn!",
4479 "You were stunned for %d turns!",
4480 force_remaining ),
4481 force_remaining );
4482 }
4483 u.add_effect( effect_stunned, 1_turns * force_remaining );
4484 }
4485 traj.erase( traj.begin(), traj.begin() + i );
4486 if( critter_at<monster>( traj.front() ) ) {
4487 add_msg( _( "You collided with something and sent it flying!" ) );
4488 } else if( npc *const guy = critter_at<npc>( traj.front() ) ) {
4489 if( guy->male ) {
4490 add_msg( _( "You collided with someone and sent him flying!" ) );
4491 } else {
4492 add_msg( _( "You collided with someone and sent her flying!" ) );
4493 }
4494 }
4495 knockback( traj, stun, dam_mult, source );
4496 break;
4497 }
4498 if( m.has_flag( "LIQUID", u.pos() ) && force_remaining == 0 ) {
4499 avatar_action::swim( m, u, u.pos() );
4500 } else {
4501 u.setpos( traj[i] );
4502 }
4503 tp = traj[i];
4504
4505 if( start_pos != u.pos() ) {
4506 map &here = get_map();
4507 here.creature_on_trap( u );
4508 }
4509 }
4510 }
4511}
double footwear_factor() const
Returns 1 if the player is wearing something on both feet, .5 if on one, and 0 if on neither.
Definition: character.cpp:8938
dealt_damage_instance deal_damage(Creature *source, bodypart_id bp, const damage_instance &d) override
Calls Creature::deal_damage and handles damaged effects (waking up, etc.)
Definition: character.cpp:8465
void add_effect(const effect &eff, bool force=false, bool deferred=false)
Definition: creature.cpp:1008
@ DT_BASH
Definition: damage.h:24
static const trait_id trait_LEG_TENT_BRACE("LEG_TENT_BRACE")
static const efftype_id effect_stunned("stunned")
@ MF_AQUATIC
Definition: mtype.h:89
void swim(map &m, avatar &you, const tripoint &p)
Handles swimming by the player.
const char * vgettext(const char *msgid, const char *msgid_plural, size_t n)

References _, Creature::add_effect(), add_msg(), map::bash(), Creature::check_dead_state(), critter_at(), Character::deal_damage(), debugmsg, DT_BASH, effect_stunned, Character::footwear_factor(), get_map, Creature::has_effect(), map::has_flag(), Character::has_trait(), anonymous_namespace{iexamine_elevator.cpp}::elevator::here(), map::impassable(), knockback(), m, m_bad, MF_AQUATIC, map::obstructed_by_vehicle_rotation(), one_in(), Character::pos(), Character::posx(), Character::posy(), Character::sees(), Character::setpos(), avatar_action::swim(), trait_LEG_TENT_BRACE, u, vgettext(), tripoint::x, tripoint::y, and tripoint::z.

◆ light_level()

unsigned char game::light_level ( int  zlev) const

Returns coarse number-of-squares of visibility at the current light level.

Used by monster and NPC AI.

Definition at line 3568 of file game.cpp.

3569{
3570 const float light = natural_light_level( zlev );
3571 return LIGHT_RANGE( light );
3572}
float natural_light_level(int zlev) const
Definition: game.cpp:3508
#define LIGHT_RANGE(b)
Definition: lightmap.h:41

References light, LIGHT_RANGE, and natural_light_level().

Referenced by calc_driving_offset(), and update_overmap_seen().

◆ list_active_saves()

std::vector< std::string > game::list_active_saves ( )

Returns a list of currently active character saves.

Definition at line 2775 of file game.cpp.

2776{
2777 std::vector<std::string> saves;
2778 for( auto &worldsave : world_generator->active_world->world_saves ) {
2779 saves.push_back( worldsave.decoded_name() );
2780 }
2781 return saves;
2782}

References world_generator.

Referenced by cleanup_at_end().

◆ list_items()

game::vmenu_ret game::list_items ( const std::vector< map_item_stack > &  item_list)
private

Definition at line 7298 of file game.cpp.

7299{
7300 std::vector<map_item_stack> ground_items = item_list;
7301 int iInfoHeight = 0;
7302 int iMaxRows = 0;
7303 int width = 0;
7304 int max_name_width = 0;
7305
7306 //find max length of item name and resize window width
7307 for( const map_item_stack &cur_item : ground_items ) {
7308 const int item_len = utf8_width( remove_color_tags( cur_item.example->display_name() ) ) + 15;
7309 if( item_len > max_name_width ) {
7310 max_name_width = item_len;
7311 }
7312 }
7313
7314 tripoint active_pos;
7315 map_item_stack *activeItem = nullptr;
7316
7317 catacurses::window w_items;
7318 catacurses::window w_items_border;
7319 catacurses::window w_item_info;
7320
7321 ui_adaptor ui;
7322 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
7323 iInfoHeight = std::min( 25, TERMY / 2 );
7324 iMaxRows = TERMY - iInfoHeight - 2;
7325
7326 width = clamp( max_name_width, 45, TERMX / 3 );
7327
7328 const int offsetX = TERMX - width;
7329
7330 w_items = catacurses::newwin( TERMY - 2 - iInfoHeight,
7331 width - 2, point( offsetX + 1, 1 ) );
7332 w_items_border = catacurses::newwin( TERMY - iInfoHeight,
7333 width, point( offsetX, 0 ) );
7334 w_item_info = catacurses::newwin( iInfoHeight, width,
7335 point( offsetX, TERMY - iInfoHeight ) );
7336
7337 if( activeItem ) {
7338 centerlistview( active_pos, width );
7339 }
7340
7341 ui.position( point( offsetX, 0 ), point( width, TERMY ) );
7342 } );
7343 ui.mark_resize();
7344
7345 // use previously selected sorting method
7346 bool sort_radius = uistate.list_item_sort != 2;
7347 bool addcategory = !sort_radius;
7348
7349 // reload filter/priority settings on the first invocation, if they were active
7350 if( !uistate.list_item_init ) {
7353 }
7356 }
7359 }
7360 uistate.list_item_init = true;
7361 }
7362
7363 //this stores only those items that match our filter
7364 std::vector<map_item_stack> filtered_items =
7365 !sFilter.empty() ? filter_item_stacks( ground_items, sFilter ) : ground_items;
7366 int highPEnd = list_filter_high_priority( filtered_items, list_item_upvote );
7367 int lowPStart = list_filter_low_priority( filtered_items, highPEnd, list_item_downvote );
7368 int iItemNum = ground_items.size();
7369
7370 const tripoint stored_view_offset = u.view_offset;
7371
7373
7374 int iActive = 0; // Item index that we're looking at
7375 bool refilter = true;
7376 int page_num = 0;
7377 int iCatSortNum = 0;
7378 int iScrollPos = 0;
7379 std::map<int, std::string> mSortCategory;
7380
7381 std::string action;
7382 input_context ctxt( "LIST_ITEMS" );
7383 ctxt.register_action( "UP", to_translation( "Move cursor up" ) );
7384 ctxt.register_action( "DOWN", to_translation( "Move cursor down" ) );
7385 ctxt.register_action( "LEFT", to_translation( "Previous item" ) );
7386 ctxt.register_action( "RIGHT", to_translation( "Next item" ) );
7387 ctxt.register_action( "PAGE_DOWN" );
7388 ctxt.register_action( "PAGE_UP" );
7389 ctxt.register_action( "NEXT_TAB" );
7390 ctxt.register_action( "PREV_TAB" );
7391 ctxt.register_action( "HELP_KEYBINDINGS" );
7392 ctxt.register_action( "QUIT" );
7393 ctxt.register_action( "FILTER" );
7394 ctxt.register_action( "RESET_FILTER" );
7395 ctxt.register_action( "EXAMINE" );
7396 ctxt.register_action( "COMPARE" );
7397 ctxt.register_action( "PRIORITY_INCREASE" );
7398 ctxt.register_action( "PRIORITY_DECREASE" );
7399 ctxt.register_action( "SORT" );
7400 ctxt.register_action( "TRAVEL_TO" );
7401
7402 std::optional<item_filter_type> filter_type;
7403
7404 ui.on_redraw( [&]( const ui_adaptor & ) {
7405 reset_item_list_state( w_items_border, iInfoHeight, sort_radius );
7406
7407 if( ground_items.empty() ) {
7408 wnoutrefresh( w_items_border );
7409 mvwprintz( w_items, point( 2, 10 ), c_white, _( "You don't see any items around you!" ) );
7410 } else {
7411 int iStartPos = 0;
7412 werase( w_items );
7413 calcStartPos( iStartPos, iActive, iMaxRows, iItemNum );
7414 int iNum = 0;
7415 bool high = false;
7416 bool low = false;
7417 int index = 0;
7418 int iCatSortOffset = 0;
7419
7420 for( int i = 0; i < iStartPos; i++ ) {
7421 if( !mSortCategory[i].empty() ) {
7422 iNum++;
7423 }
7424 }
7425 for( auto iter = filtered_items.begin(); iter != filtered_items.end(); ++index ) {
7426 if( highPEnd > 0 && index < highPEnd + iCatSortOffset ) {
7427 high = true;
7428 low = false;
7429 } else if( index >= lowPStart + iCatSortOffset ) {
7430 high = false;
7431 low = true;
7432 } else {
7433 high = false;
7434 low = false;
7435 }
7436
7437 if( iNum >= iStartPos && iNum < iStartPos + ( iMaxRows > iItemNum ? iItemNum : iMaxRows ) ) {
7438 int iThisPage = 0;
7439 if( !mSortCategory[iNum].empty() ) {
7440 iCatSortOffset++;
7441 mvwprintz( w_items, point( 1, iNum - iStartPos ), c_magenta, mSortCategory[iNum] );
7442 } else {
7443 if( iNum == iActive ) {
7444 iThisPage = page_num;
7445 }
7446 std::string sText;
7447 if( iter->vIG.size() > 1 ) {
7448 sText += string_format( "[%d/%d] (%d) ", iThisPage + 1, iter->vIG.size(), iter->totalcount );
7449 }
7450 sText += iter->example->tname();
7451 if( iter->vIG[iThisPage].count > 1 ) {
7452 sText += string_format( "[%d]", iter->vIG[iThisPage].count );
7453 }
7454
7455 nc_color col = c_light_green;
7456 if( iNum != iActive ) {
7457 if( high ) {
7458 col = c_yellow;
7459 } else if( low ) {
7460 col = c_red;
7461 } else {
7462 col = iter->example->color_in_inventory();
7463 }
7464 }
7465 trim_and_print( w_items, point( 1, iNum - iStartPos ), width - 9, col, sText );
7466 const int numw = iItemNum > 9 ? 2 : 1;
7467 const int x = iter->vIG[iThisPage].pos.x;
7468 const int y = iter->vIG[iThisPage].pos.y;
7469 mvwprintz( w_items, point( width - 6 - numw, iNum - iStartPos ),
7470 iNum == iActive ? c_light_green : c_light_gray,
7471 "%*d %s", numw, rl_dist( point_zero, point( x, y ) ),
7473 ++iter;
7474 }
7475 } else {
7476 ++iter;
7477 }
7478 iNum++;
7479 }
7480 iNum = 0;
7481 for( int i = 0; i < iActive; i++ ) {
7482 if( !mSortCategory[i].empty() ) {
7483 iNum++;
7484 }
7485 }
7486 mvwprintz( w_items_border, point( ( width - 9 ) / 2 + ( iItemNum > 9 ? 0 : 1 ), 0 ),
7487 c_light_green, " %*d", iItemNum > 9 ? 2 : 1, iItemNum > 0 ? iActive - iNum + 1 : 0 );
7488 wprintz( w_items_border, c_white, " / %*d ", iItemNum > 9 ? 2 : 1, iItemNum - iCatSortNum );
7489 werase( w_item_info );
7490
7491 if( iItemNum > 0 && activeItem ) {
7492 item_location loc( map_cursor( u.pos() + activeItem->example_item_pos ),
7493 const_cast<item *>( activeItem->example ) );
7495 std::vector<iteminfo> this_item = activeItem->example->info( temperature );
7496 std::vector<iteminfo> item_info_dummy;
7497
7498 item_info_data dummy( "", "", this_item, item_info_dummy, iScrollPos );
7499 dummy.without_getch = true;
7500 dummy.without_border = true;
7501
7502 draw_item_info( w_item_info, dummy );
7503 }
7504 draw_scrollbar( w_items_border, iActive, iMaxRows, iItemNum, point_south );
7505 wnoutrefresh( w_items_border );
7506 }
7507
7508 const bool bDrawLeft = ground_items.empty() || filtered_items.empty() || !activeItem || filter_type;
7509 draw_custom_border( w_item_info, bDrawLeft, true, true, true, LINE_XXXO, LINE_XOXX, true, true );
7510
7511 if( iItemNum > 0 && activeItem ) {
7512 // print info window title: < item name >
7513 mvwprintw( w_item_info, point( 2, 0 ), "< " );
7514 trim_and_print( w_item_info, point( 4, 0 ), width - 8, activeItem->example->color_in_inventory(),
7515 activeItem->example->display_name() );
7516 wprintw( w_item_info, " >" );
7517 }
7518
7519 wnoutrefresh( w_items );
7520 wnoutrefresh( w_item_info );
7521
7522 if( filter_type ) {
7523 draw_item_filter_rules( w_item_info, 0, iInfoHeight - 1, filter_type.value() );
7524 }
7525 } );
7526
7527 std::optional<tripoint> trail_start;
7528 std::optional<tripoint> trail_end;
7529 bool trail_end_x = false;
7530 shared_ptr_fast<draw_callback_t> trail_cb = create_trail_callback( trail_start, trail_end,
7531 trail_end_x );
7532 add_draw_callback( trail_cb );
7533
7534 do {
7535 if( action == "COMPARE" && activeItem ) {
7536 game_menus::inv::compare( u, active_pos );
7537 } else if( action == "FILTER" ) {
7538 filter_type = item_filter_type::FILTER;
7539 ui.invalidate_ui();
7541 .title( _( "Filter:" ) )
7542 .width( 55 )
7543 .description( _( "UP: history, CTRL-U: clear line, ESC: abort, ENTER: save" ) )
7544 .identifier( "item_filter" )
7545 .max_length( 256 )
7546 .edit( sFilter );
7547 refilter = true;
7548 addcategory = !sort_radius;
7550 filter_type = std::nullopt;
7551 } else if( action == "RESET_FILTER" ) {
7552 sFilter.clear();
7553 filtered_items = ground_items;
7554 refilter = true;
7556 addcategory = !sort_radius;
7557 } else if( action == "EXAMINE" && !filtered_items.empty() && activeItem ) {
7558 std::vector<iteminfo> dummy;
7559 const item *example_item = activeItem->example;
7560 // TODO: const_item_location
7561 item_location loc = item_location( u, const_cast<item *>( example_item ) );
7563 std::vector<iteminfo> this_item = example_item->info( temperature );
7564
7565 item_info_data info_data( example_item->tname(), example_item->type_name(), this_item, dummy );
7566 info_data.handle_scrolling = true;
7567
7569 return catacurses::newwin( TERMY, width - 5, point_zero );
7570 }, info_data );
7571 } else if( action == "PRIORITY_INCREASE" ) {
7572 filter_type = item_filter_type::HIGH_PRIORITY;
7573 ui.invalidate_ui();
7575 .title( _( "High Priority:" ) )
7576 .width( 55 )
7578 .description( _( "UP: history, CTRL-U clear line, ESC: abort, ENTER: save" ) )
7579 .identifier( "list_item_priority" )
7580 .max_length( 256 )
7581 .query_string();
7582 refilter = true;
7583 addcategory = !sort_radius;
7585 filter_type = std::nullopt;
7586 } else if( action == "PRIORITY_DECREASE" ) {
7587 filter_type = item_filter_type::LOW_PRIORITY;
7588 ui.invalidate_ui();
7590 .title( _( "Low Priority:" ) )
7591 .width( 55 )
7593 .description( _( "UP: history, CTRL-U clear line, ESC: abort, ENTER: save" ) )
7594 .identifier( "list_item_downvote" )
7595 .max_length( 256 )
7596 .query_string();
7597 refilter = true;
7598 addcategory = !sort_radius;
7600 filter_type = std::nullopt;
7601 } else if( action == "SORT" ) {
7602 if( sort_radius ) {
7603 sort_radius = false;
7604 addcategory = true;
7605 uistate.list_item_sort = 2; // list is sorted by category
7606 } else {
7607 sort_radius = true;
7608 uistate.list_item_sort = 1; // list is sorted by distance
7609 }
7610 highPEnd = -1;
7611 lowPStart = -1;
7612 iCatSortNum = 0;
7613
7614 mSortCategory.clear();
7615 refilter = true;
7616 } else if( action == "TRAVEL_TO" && activeItem ) {
7617 if( !u.sees( u.pos() + active_pos ) ) {
7618 add_msg( _( "You can't see that destination." ) );
7619 }
7620 auto route = m.route( u.pos(), u.pos() + active_pos, u.get_pathfinding_settings(),
7621 u.get_path_avoid() );
7622 if( route.size() > 1 ) {
7623 route.pop_back();
7624 u.set_destination( route );
7625 break;
7626 } else {
7627 add_msg( m_info, _( "You can't travel there." ) );
7628 }
7629 }
7630 if( uistate.list_item_sort == 1 ) {
7631 ground_items = item_list;
7632 } else if( uistate.list_item_sort == 2 ) {
7633 std::sort( ground_items.begin(), ground_items.end(), map_item_stack::map_item_stack_sort );
7634 }
7635
7636 if( refilter ) {
7637 refilter = false;
7638 filtered_items = filter_item_stacks( ground_items, sFilter );
7639 highPEnd = list_filter_high_priority( filtered_items, list_item_upvote );
7640 lowPStart = list_filter_low_priority( filtered_items, highPEnd, list_item_downvote );
7641 iActive = 0;
7642 page_num = 0;
7643 iItemNum = filtered_items.size();
7644 }
7645
7646 if( addcategory ) {
7647 addcategory = false;
7648 iCatSortNum = 0;
7649 mSortCategory.clear();
7650 if( highPEnd > 0 ) {
7651 mSortCategory[0] = _( "HIGH PRIORITY" );
7652 iCatSortNum++;
7653 }
7654 std::string last_cat_name;
7655 for( int i = std::max( 0, highPEnd );
7656 i < std::min( lowPStart, static_cast<int>( filtered_items.size() ) ); i++ ) {
7657 const std::string &cat_name = filtered_items[i].example->get_category().name();
7658 if( cat_name != last_cat_name ) {
7659 mSortCategory[i + iCatSortNum++] = cat_name;
7660 last_cat_name = cat_name;
7661 }
7662 }
7663 if( lowPStart < static_cast<int>( filtered_items.size() ) ) {
7664 mSortCategory[lowPStart + iCatSortNum++] = _( "LOW PRIORITY" );
7665 }
7666 if( !mSortCategory[0].empty() ) {
7667 iActive++;
7668 }
7669 iItemNum = static_cast<int>( filtered_items.size() ) + iCatSortNum;
7670 }
7671
7672 if( action == "UP" ) {
7673 do {
7674 iActive--;
7675
7676 } while( !mSortCategory[iActive].empty() );
7677 iScrollPos = 0;
7678 page_num = 0;
7679 if( iActive < 0 ) {
7680 iActive = iItemNum - 1;
7681 }
7682 } else if( action == "DOWN" ) {
7683 do {
7684 iActive++;
7685
7686 } while( !mSortCategory[iActive].empty() );
7687 iScrollPos = 0;
7688 page_num = 0;
7689 if( iActive >= iItemNum ) {
7690 iActive = mSortCategory[0].empty() ? 0 : 1;
7691 }
7692 } else if( action == "RIGHT" ) {
7693 if( !filtered_items.empty() && activeItem ) {
7694 if( ++page_num >= static_cast<int>( activeItem->vIG.size() ) ) {
7695 page_num = activeItem->vIG.size() - 1;
7696 }
7697 }
7698 } else if( action == "LEFT" ) {
7699 page_num = std::max( 0, page_num - 1 );
7700 } else if( action == "PAGE_UP" ) {
7701 iScrollPos--;
7702 } else if( action == "PAGE_DOWN" ) {
7703 iScrollPos++;
7704 } else if( action == "NEXT_TAB" || action == "PREV_TAB" ) {
7705 u.view_offset = stored_view_offset;
7707 }
7708
7709 active_pos = tripoint_zero;
7710 activeItem = nullptr;
7711
7712 if( mSortCategory[iActive].empty() ) {
7713 auto iter = filtered_items.begin();
7714 for( int iNum = 0; iter != filtered_items.end() && iNum < iActive; iNum++ ) {
7715 if( mSortCategory[iNum].empty() ) {
7716 ++iter;
7717 }
7718 }
7719 if( iter != filtered_items.end() ) {
7720 active_pos = iter->vIG[page_num].pos;
7721 activeItem = &( *iter );
7722 }
7723 }
7724
7725 if( activeItem ) {
7726 centerlistview( active_pos, width );
7727 trail_start = u.pos();
7728 trail_end = u.pos() + active_pos;
7729 // Actually accessed from the terrain overlay callback `trail_cb` in the
7730 // call to `ui_manager::redraw`.
7731 //NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
7732 trail_end_x = true;
7733 } else {
7734 u.view_offset = stored_view_offset;
7735 trail_start = trail_end = std::nullopt;
7736 }
7738
7740
7741 action = ctxt.handle_input();
7742 } while( action != "QUIT" );
7743
7744 u.view_offset = stored_view_offset;
7745 return game::vmenu_ret::QUIT;
7746}
constexpr T clamp(const T &val, const T &min, const T &max)
Clamp first argument so that it is no lower than second and no higher than third.
Definition: cata_utility.h:149
std::string list_item_upvote
Definition: game.h:1030
std::string list_item_downvote
Definition: game.h:1031
std::string sFilter
Definition: game.h:1029
void reset_item_list_state(const catacurses::window &window, int height, bool bRadiusSort)
Definition: game.cpp:7184
std::vector< iteminfo > info() const
Return all the information about the item and its type as a vector.
Definition: item.cpp:3992
nc_color color_in_inventory() const
Returns the color of the item depending on usefulness for the player character, e....
Definition: item.cpp:4148
std::string type_name(unsigned int quantity=1) const
Name of the item type (not the item), with proper plural.
Definition: item.cpp:9881
static bool map_item_stack_sort(const map_item_stack &lhs, const map_item_stack &rhs)
std::vector< item_group > vIG
const item * example
tripoint example_item_pos
string_input_popup & identifier(const std::string &value)
An identifier to be used to store / get the input history.
string_input_popup & text(const std::string &value)
Set / get the text that can be modified by the user.
void edit(std::string &value)
Edit values in place.
string_input_popup & width(int value)
Width (in console cells) of the input field itself.
string_input_popup & description(const std::string &value)
Additional help text, shown below the input box.
string_input_popup & title(const std::string &value)
The title: short string before the actual input field.
std::string list_item_priority
Definition: uistate.h:121
int list_item_sort
Definition: uistate.h:118
bool list_item_downvote_active
Definition: uistate.h:124
bool list_item_init
Definition: uistate.h:126
bool list_item_filter_active
Definition: uistate.h:123
std::string list_item_filter
Definition: uistate.h:119
bool list_item_priority_active
Definition: uistate.h:125
std::string list_item_downvote
Definition: uistate.h:120
direction direction_from(const coords::coord_point< Point, Origin, Scale > &loc1, const coords::coord_point< Point, Origin, Scale > &loc2)
Definition: coordinates.h:540
temperature_flag
Definition: enums.h:42
static shared_ptr_fast< game::draw_callback_t > create_trail_callback(const std::optional< tripoint > &trail_start, const std::optional< tripoint > &trail_end, const bool &trail_end_x)
Definition: game.cpp:3088
uistatedata uistate
Definition: game.cpp:288
static void centerlistview(const tripoint &active_item_position, int ui_width)
Definition: game.cpp:7029
std::string direction_name_short(const direction dir)
Definition: line.cpp:533
int list_filter_high_priority(std::vector< map_item_stack > &stack, const std::string &priorities)
std::vector< map_item_stack > filter_item_stacks(const std::vector< map_item_stack > &stack, const std::string &filter)
int list_filter_low_priority(std::vector< map_item_stack > &stack, const int start, const std::string &priorities)
void mvwprintw(const window &win, point p, const std::string &text)
void wprintw(const window &win, const std::string &text)
temperature_flag temperature_flag_for_location(const map &m, const item_location &loc)
Definition: rot.cpp:13
quantity< int, temperature_in_millidegree_celsius_tag > temperature
void calcStartPos(int &iStartPos, const int iCurrentLine, const int iContentHeight, const int iNumEntries)
Definition: output.cpp:1507
void draw_custom_border(const catacurses::window &w, const catacurses::chtype ls, const catacurses::chtype rs, const catacurses::chtype ts, const catacurses::chtype bs, const catacurses::chtype tl, const catacurses::chtype tr, const catacurses::chtype bl, const catacurses::chtype br, const nc_color FG, point pos, int height, int width)
Definition: output.cpp:524
void draw_item_filter_rules(const catacurses::window &win, int starty, int height, item_filter_type type)
Write some tips (such as precede items with - to exclude them) onto the window.
Definition: output.cpp:810
std::string remove_color_tags(const std::string &s)
Removes the color tags from the input string.
Definition: output.cpp:145
void trim_and_print(const catacurses::window &w, point begin, const int width, const nc_color &base_color, const std::string &text, const report_color_error color_error)
Prints a single line of text.
Definition: output.cpp:214
void draw_scrollbar(const catacurses::window &window, const int iCurrentLine, const int iContentHeight, const int iNumLines, point offset, nc_color bar_color, const bool bDoNotScrollToEnd)
Draw a scrollbar (Legacy function, use class scrollbar instead!)
Definition: output.cpp:1314
input_event draw_item_info(const int iLeft, const int iWidth, const int iTop, const int iHeight, item_info_data &data)
Definition: output.cpp:793
#define LINE_XOXX
Definition: output.h:47
#define LINE_XXXO
Definition: output.h:45

References _, action, add_draw_callback(), add_msg(), c_light_gray, c_light_green, c_magenta, c_red, c_white, c_yellow, calcStartPos(), centerlistview(), CHANGE_TAB, clamp(), item::color_in_inventory(), game_menus::inv::compare(), create_trail_callback(), string_input_popup::description(), direction_from(), direction_name_short(), item::display_name(), draw_custom_border(), draw_item_filter_rules(), draw_item_info(), draw_scrollbar(), string_input_popup::edit(), map_item_stack::example, map_item_stack::example_item_pos, FILTER, filter_item_stacks(), Character::get_path_avoid(), Character::get_pathfinding_settings(), input_context::handle_input(), item_info_data::handle_scrolling, high, HIGH_PRIORITY, string_input_popup::identifier(), item::info(), invalidate_main_ui_adaptor(), LINE_XOXX, LINE_XXXO, list_filter_high_priority(), list_filter_low_priority(), list_item_downvote, uistatedata::list_item_downvote, uistatedata::list_item_downvote_active, uistatedata::list_item_filter, uistatedata::list_item_filter_active, uistatedata::list_item_init, uistatedata::list_item_priority, uistatedata::list_item_priority_active, uistatedata::list_item_sort, list_item_upvote, LOW_PRIORITY, m, m_info, map_item_stack::map_item_stack_sort(), string_input_popup::max_length(), catacurses::mvwprintw(), mvwprintz(), catacurses::newwin(), point_south, point_zero, Character::pos(), string_input_popup::query_string(), QUIT, ui_manager::redraw(), input_context::register_action(), remove_color_tags(), reset_item_list_state(), rl_dist(), map::route(), Character::sees(), Character::set_destination(), sFilter, string_format(), rot::temperature_flag_for_location(), TERMX, TERMY, string_input_popup::text(), string_input_popup::title(), item::tname(), to_translation(), trim_and_print(), tripoint_zero, item::type_name(), u, uistate, utf8_width(), player::view_offset, map_item_stack::vIG, catacurses::werase(), string_input_popup::width(), item_info_data::without_border, item_info_data::without_getch, catacurses::wnoutrefresh(), catacurses::wprintw(), and wprintz().

Referenced by list_items_monsters().

◆ list_items_monsters()

void game::list_items_monsters ( )
private

Definition at line 7253 of file game.cpp.

7254{
7255 std::vector<Creature *> mons = u.get_visible_creatures( current_daylight_level( calendar::turn ) );
7256 // whole reality bubble
7257 const std::vector<map_item_stack> items = find_nearby_items( 60 );
7258
7259 if( mons.empty() && items.empty() ) {
7260 add_msg( m_info, _( "You don't see any items or monsters around you!" ) );
7261 return;
7262 }
7263
7264 std::sort( mons.begin(), mons.end(), [&]( const Creature * lhs, const Creature * rhs ) {
7265 const auto att_lhs = lhs->attitude_to( u );
7266 const auto att_rhs = rhs->attitude_to( u );
7267
7268 return att_lhs < att_rhs || ( att_lhs == att_rhs
7269 && rl_dist( u.pos(), lhs->pos() ) < rl_dist( u.pos(), rhs->pos() ) );
7270 } );
7271
7272 // If the current list is empty, switch to the non-empty list
7274 if( items.empty() ) {
7275 uistate.vmenu_show_items = false;
7276 }
7277 } else if( mons.empty() ) {
7279 }
7280
7283 while( true ) {
7284 ret = uistate.vmenu_show_items ? list_items( items ) : list_monsters( mons );
7287 } else {
7288 break;
7289 }
7290 }
7291
7292 if( ret == game::vmenu_ret::FIRE ) {
7294 }
7296}
double current_daylight_level(const time_point &p)
Returns the current seasonally-adjusted maximum daylight level.
Definition: calendar.cpp:171
game::vmenu_ret list_monsters(const std::vector< Creature * > &monster_list)
Definition: game.cpp:7748
game::vmenu_ret list_items(const std::vector< map_item_stack > &item_list)
Definition: game.cpp:7298
vmenu_ret
Definition: game.h:767
std::vector< map_item_stack > find_nearby_items(int iRadius)
Definition: game.cpp:6952
void temp_exit_fullscreen()
Definition: game.cpp:457
void reenter_fullscreen()
Definition: game.cpp:467
bool vmenu_show_items
Definition: uistate.h:122

References _, add_msg(), CHANGE_TAB, current_daylight_level(), find_nearby_items(), FIRE, avatar_action::fire_wielded_weapon(), Character::get_visible_creatures(), list_items(), list_monsters(), m_info, reenter_fullscreen(), cata::hash64_detail::ret, temp_exit_fullscreen(), calendar::turn, u, uistate, and uistatedata::vmenu_show_items.

Referenced by handle_action(), and look_around().

◆ list_missions()

void game::list_missions ( )

Definition at line 22 of file mission_ui.cpp.

23{
24 catacurses::window w_missions;
25
26 enum class tab_mode : int {
27 TAB_ACTIVE = 0,
28 TAB_COMPLETED,
29 TAB_FAILED,
30 NUM_TABS,
31 FIRST_TAB = 0,
32 LAST_TAB = NUM_TABS - 1
33 };
34 tab_mode tab = tab_mode::FIRST_TAB;
35 size_t selection = 0;
36 int entries_per_page = 0;
37 input_context ctxt( "MISSIONS" );
38 ctxt.register_cardinal();
39 ctxt.register_action( "CONFIRM" );
40 ctxt.register_action( "QUIT" );
41 ctxt.register_action( "HELP_KEYBINDINGS" );
42
44 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
46
47 // content ranges from y=3 to FULL_SCREEN_HEIGHT - 2
48 entries_per_page = FULL_SCREEN_HEIGHT - 4;
49
50 ui.position_from_window( w_missions );
51 } );
52 ui.mark_resize();
53
54 std::vector<mission *> umissions;
55
56 ui.on_redraw( [&]( const ui_adaptor & ) {
57 werase( w_missions );
58 // entries_per_page * page number
59 const int top_of_page = entries_per_page * ( selection / entries_per_page );
60 const int bottom_of_page =
61 std::min( top_of_page + entries_per_page - 1, static_cast<int>( umissions.size() ) - 1 );
62
63 for( int i = 3; i < FULL_SCREEN_HEIGHT - 1; i++ ) {
64 mvwputch( w_missions, point( 30, i ), BORDER_COLOR, LINE_XOXO );
65 }
66
67 const std::vector<std::pair<tab_mode, std::string>> tabs = {
68 { tab_mode::TAB_ACTIVE, _( "ACTIVE MISSIONS" ) },
69 { tab_mode::TAB_COMPLETED, _( "COMPLETED MISSIONS" ) },
70 { tab_mode::TAB_FAILED, _( "FAILED MISSIONS" ) },
71 };
72 draw_tabs( w_missions, tabs, tab );
73 draw_border_below_tabs( w_missions );
74
75 mvwputch( w_missions, point( 30, 2 ), BORDER_COLOR,
76 tab == tab_mode::TAB_COMPLETED ? ' ' : LINE_OXXX ); // ^|^
77 mvwputch( w_missions, point( 30, FULL_SCREEN_HEIGHT - 1 ), BORDER_COLOR, LINE_XXOX ); // _|_
78
79 draw_scrollbar( w_missions, selection, entries_per_page, umissions.size(), point( 0, 3 ) );
80
81 for( int i = top_of_page; i <= bottom_of_page; i++ ) {
82 const auto miss = umissions[i];
83 const nc_color col = u.get_active_mission() == miss ? c_light_green : c_white;
84 const int y = i - top_of_page + 3;
85 trim_and_print( w_missions, point( 1, y ), 28,
86 static_cast<int>( selection ) == i ? hilite( col ) : col,
87 miss->name() );
88 }
89
90 if( selection < umissions.size() ) {
91 const auto miss = umissions[selection];
92 const nc_color col = u.get_active_mission() == miss ? c_light_green : c_white;
93 std::string for_npc;
94 if( miss->get_npc_id().is_valid() ) {
95 npc *guy = g->find_npc( miss->get_npc_id() );
96 if( guy ) {
97 for_npc = string_format( _( " for %s" ), guy->disp_name() );
98 }
99 }
100
101 int y = 3;
102 y += fold_and_print( w_missions, point( 31, y ), getmaxx( w_missions ) - 33, col,
103 miss->name() + for_npc );
104
105 auto format_tokenized_description = []( const std::string & description,
106 const std::vector<std::pair<int, itype_id>> &rewards ) {
107 std::string formatted_description = description;
108 for( const auto &reward : rewards ) {
109 std::string token = "<reward_count:" + reward.second.str() + ">";
110 formatted_description = replace_all( formatted_description, token,
111 string_format( "%d", reward.first ) );
112 }
113 return formatted_description;
114 };
115
116 y++;
117 if( !miss->get_description().empty() ) {
118 y += fold_and_print( w_missions, point( 31, y ), getmaxx( w_missions ) - 33, c_white,
119 format_tokenized_description( miss->get_description(), miss->get_likely_rewards() ) );
120 }
121 if( miss->has_deadline() ) {
122 const time_point deadline = miss->get_deadline();
123 mvwprintz( w_missions, point( 31, ++y ), c_white, _( "Deadline: %s" ), to_string( deadline ) );
124
125 if( tab != tab_mode::TAB_COMPLETED ) {
126 // There's no point in displaying this for a completed mission.
127 // @ TODO: But displaying when you completed it would be useful.
128 const time_duration remaining = deadline - calendar::turn;
129 std::string remaining_time;
130
131 if( remaining <= 0_turns ) {
132 remaining_time = _( "None!" );
133 } else if( u.has_watch() ) {
134 remaining_time = to_string( remaining );
135 } else {
136 remaining_time = to_string_approx( remaining );
137 }
138
139 mvwprintz( w_missions, point( 31, ++y ), c_white, _( "Time remaining: %s" ), remaining_time );
140 }
141 }
142 if( miss->has_target() ) {
144 // TODO: target does not contain a z-component, targets are assumed to be on z=0
145 mvwprintz( w_missions, point( 31, ++y ), c_white, _( "Target: %s You: %s" ),
146 miss->get_target().to_string(), pos.to_string() );
147 }
148 } else {
149 static const std::map< tab_mode, std::string > nope = {
150 { tab_mode::TAB_ACTIVE, translate_marker( "You have no active missions!" ) },
151 { tab_mode::TAB_COMPLETED, translate_marker( "You haven't completed any missions!" ) },
152 { tab_mode::TAB_FAILED, translate_marker( "You haven't failed any missions!" ) }
153 };
154 mvwprintz( w_missions, point( 31, 4 ), c_light_red, _( nope.at( tab ) ) );
155 }
156
157 wnoutrefresh( w_missions );
158 } );
159
160 while( true ) {
161 umissions.clear();
162 if( tab < tab_mode::FIRST_TAB || tab >= tab_mode::NUM_TABS ) {
163 debugmsg( "The sanity check failed because tab=%d", static_cast<int>( tab ) );
164 tab = tab_mode::FIRST_TAB;
165 }
166 switch( tab ) {
168 umissions = u.get_active_missions();
169 break;
170 case tab_mode::TAB_COMPLETED:
171 umissions = u.get_completed_missions();
172 break;
173 case tab_mode::TAB_FAILED:
174 umissions = u.get_failed_missions();
175 break;
176 default:
177 break;
178 }
179 if( ( !umissions.empty() && selection >= umissions.size() ) ||
180 ( umissions.empty() && selection != 0 ) ) {
181 debugmsg( "Sanity check failed: selection=%d, size=%d", static_cast<int>( selection ),
182 static_cast<int>( umissions.size() ) );
183 selection = 0;
184 }
186 const std::string action = ctxt.handle_input();
187 if( action == "RIGHT" ) {
188 tab = static_cast<tab_mode>( static_cast<int>( tab ) + 1 );
189 if( tab >= tab_mode::NUM_TABS ) {
190 tab = tab_mode::FIRST_TAB;
191 }
192 selection = 0;
193 } else if( action == "LEFT" ) {
194 tab = static_cast<tab_mode>( static_cast<int>( tab ) - 1 );
195 if( tab < tab_mode::FIRST_TAB ) {
196 tab = tab_mode::LAST_TAB;
197 }
198 selection = 0;
199 } else if( action == "DOWN" ) {
200 selection++;
201 if( selection >= umissions.size() ) {
202 selection = 0;
203 }
204 } else if( action == "UP" ) {
205 if( selection == 0 ) {
206 selection = umissions.empty() ? 0 : umissions.size() - 1;
207 } else {
208 selection--;
209 }
210 } else if( action == "CONFIRM" ) {
211 if( tab == tab_mode::TAB_ACTIVE && selection < umissions.size() ) {
212 u.set_active_mission( *umissions[selection] );
213 }
214 break;
215 } else if( action == "QUIT" ) {
216 break;
217 }
218 }
219}
std::string to_string_approx(const time_duration &dur, const bool verbose)
Returns approximate duration.
Definition: calendar.cpp:361
bool has_watch() const
Returns true if the player or their vehicle has a watch.
Definition: character.cpp:732
void set_active_mission(mission &cur_mission)
Set which mission is active.
Definition: avatar.cpp:215
mission * get_active_mission() const
Returns the mission that is currently active.
Definition: avatar.cpp:194
std::vector< mission * > get_completed_missions() const
Definition: avatar.cpp:184
std::vector< mission * > get_active_missions() const
Definition: avatar.cpp:179
std::vector< mission * > get_failed_missions() const
Definition: avatar.cpp:189
A point in the game time.
Definition: calendar.h:431
nc_color hilite(const nc_color &c)
Definition: color.cpp:509
void draw_tabs(const catacurses::window &w, const std::vector< std::string > &tab_texts, size_t current_tab)
Definition: output.cpp:1274
void draw_border_below_tabs(const catacurses::window &w, nc_color border_color)
Definition: output.cpp:587
int fold_and_print(const catacurses::window &w, point begin, int width, const nc_color &base_color, const std::string &text, const char split)
Fold and print text in the given window.
Definition: output.cpp:299
#define LINE_XXOX
Definition: output.h:46
#define BORDER_COLOR
Definition: output.h:92
std::string replace_all(std::string input, const std::string &what, const std::string &with)
Replace all occurences of 'what' within 'input' with 'with'.
#define translate_marker(x)
Marks a string literal to be extracted for translation.
Definition: translations.h:30
catacurses::window new_centered_win(int nlines, int ncols)
Definition: ui.cpp:30

References _, action, BORDER_COLOR, c_light_green, c_light_red, c_white, debugmsg, Character::disp_name(), draw_border_below_tabs(), draw_scrollbar(), draw_tabs(), fold_and_print(), FULL_SCREEN_HEIGHT, FULL_SCREEN_WIDTH, g, avatar::get_active_mission(), avatar::get_active_missions(), avatar::get_completed_missions(), avatar::get_failed_missions(), catacurses::getmaxx(), Character::global_omt_location(), input_context::handle_input(), Character::has_watch(), hilite(), LINE_OXXX, LINE_XOXO, LINE_XXOX, mvwprintz(), mvwputch(), new_centered_win(), ui_manager::redraw(), input_context::register_action(), input_context::register_cardinal(), replace_all(), avatar::set_active_mission(), string_format(), anonymous_namespace{bionics_ui.cpp}::TAB_ACTIVE, coords::coord_point< Point, Origin, Scale >::to_string(), to_string(), to_string_approx(), translate_marker, trim_and_print(), calendar::turn, u, catacurses::werase(), and catacurses::wnoutrefresh().

Referenced by handle_action().

◆ list_monsters()

game::vmenu_ret game::list_monsters ( const std::vector< Creature * > &  monster_list)
private

Definition at line 7748 of file game.cpp.

7749{
7750 const int iInfoHeight = 15;
7751 const int width = 45;
7752 int offsetX = 0;
7753 int iMaxRows = 0;
7754
7755 catacurses::window w_monsters;
7756 catacurses::window w_monsters_border;
7757 catacurses::window w_monster_info;
7758 catacurses::window w_monster_info_border;
7759
7760 Creature *cCurMon = nullptr;
7761 tripoint iActivePos;
7762
7763 bool hide_ui = false;
7764
7765 ui_adaptor ui;
7766 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
7767 if( hide_ui ) {
7768 ui.position( point_zero, point_zero );
7769 } else {
7770 offsetX = TERMX - width;
7771 iMaxRows = TERMY - iInfoHeight - 1;
7772
7773 w_monsters = catacurses::newwin( iMaxRows, width - 2, point( offsetX + 1,
7774 1 ) );
7775 w_monsters_border = catacurses::newwin( iMaxRows + 1, width, point( offsetX,
7776 0 ) );
7777 w_monster_info = catacurses::newwin( iInfoHeight - 2, width - 2,
7778 point( offsetX + 1, TERMY - iInfoHeight + 1 ) );
7779 w_monster_info_border = catacurses::newwin( iInfoHeight, width, point( offsetX,
7780 TERMY - iInfoHeight ) );
7781
7782 if( cCurMon ) {
7783 centerlistview( iActivePos, width );
7784 }
7785
7786 ui.position( point( offsetX, 0 ), point( width, TERMY ) );
7787 }
7788 } );
7789 ui.mark_resize();
7790
7791 const int max_gun_range = u.primary_weapon().gun_range( &u );
7792
7793 const tripoint stored_view_offset = u.view_offset;
7795
7796 int iActive = 0; // monster index that we're looking at
7797
7798 std::string action;
7799 input_context ctxt( "LIST_MONSTERS" );
7800 ctxt.register_action( "UP", to_translation( "Move cursor up" ) );
7801 ctxt.register_action( "DOWN", to_translation( "Move cursor down" ) );
7802 ctxt.register_action( "NEXT_TAB" );
7803 ctxt.register_action( "PREV_TAB" );
7804 ctxt.register_action( "SAFEMODE_BLACKLIST_ADD" );
7805 ctxt.register_action( "SAFEMODE_BLACKLIST_REMOVE" );
7806 ctxt.register_action( "QUIT" );
7807 if( bVMonsterLookFire ) {
7808 ctxt.register_action( "look" );
7809 ctxt.register_action( "fire" );
7810 }
7811 ctxt.register_action( "HELP_KEYBINDINGS" );
7812
7813 // first integer is the row the attitude category string is printed in the menu
7814 std::map<int, Creature::Attitude> mSortCategory;
7815
7816 for( int i = 0, last_attitude = -1; i < static_cast<int>( monster_list.size() ); i++ ) {
7817 const auto attitude = monster_list[i]->attitude_to( u );
7818 if( attitude != last_attitude ) {
7819 mSortCategory[i + mSortCategory.size()] = attitude;
7820 last_attitude = attitude;
7821 }
7822 }
7823
7824 ui.on_redraw( [&]( const ui_adaptor & ) {
7825 if( !hide_ui ) {
7826 draw_custom_border( w_monsters_border, true, true, true, true, true, true, LINE_XOXO, LINE_XOXO );
7827 draw_custom_border( w_monster_info_border, true, true, true, true, LINE_XXXO, LINE_XOXX, true,
7828 true );
7829
7830 mvwprintz( w_monsters_border, point( 2, 0 ), c_light_green, "<Tab> " );
7831 wprintz( w_monsters_border, c_white, _( "Monsters" ) );
7832
7833 if( monster_list.empty() ) {
7834 werase( w_monsters );
7835 mvwprintz( w_monsters, point( 2, iMaxRows / 3 ), c_white,
7836 _( "You don't see any monsters around you!" ) );
7837 } else {
7838 werase( w_monsters );
7839
7840 const int iNumMonster = monster_list.size();
7841 const int iMenuSize = monster_list.size() + mSortCategory.size();
7842
7843 const int numw = iNumMonster > 999 ? 4 :
7844 iNumMonster > 99 ? 3 :
7845 iNumMonster > 9 ? 2 : 1;
7846
7847 // given the currently selected monster iActive. get the selected row
7848 int iSelPos = iActive;
7849 for( auto &ia : mSortCategory ) {
7850 int index = ia.first;
7851 if( index <= iSelPos ) {
7852 ++iSelPos;
7853 } else {
7854 break;
7855 }
7856 }
7857 int iStartPos = 0;
7858 // use selected row get the start row
7859 calcStartPos( iStartPos, iSelPos, iMaxRows - 1, iMenuSize );
7860
7861 // get first visible monster and category
7862 int iCurMon = iStartPos;
7863 auto CatSortIter = mSortCategory.cbegin();
7864 while( CatSortIter != mSortCategory.cend() && CatSortIter->first < iStartPos ) {
7865 ++CatSortIter;
7866 --iCurMon;
7867 }
7868
7869 const auto endY = std::min<int>( iMaxRows - 1, iMenuSize );
7870 for( int y = 0; y < endY; ++y ) {
7871 if( CatSortIter != mSortCategory.cend() ) {
7872 const int iCurPos = iStartPos + y;
7873 const int iCatPos = CatSortIter->first;
7874 if( iCurPos == iCatPos ) {
7875 const std::string cat_name = Creature::get_attitude_ui_data(
7876 CatSortIter->second ).first.translated();
7877 mvwprintz( w_monsters, point( 1, y ), c_magenta, cat_name );
7878 ++CatSortIter;
7879 continue;
7880 }
7881 }
7882 // select current monster
7883 const auto critter = monster_list[iCurMon];
7884 const bool selected = iCurMon == iActive;
7885 ++iCurMon;
7886 if( critter->sees( g->u ) ) {
7887 mvwprintz( w_monsters, point( 0, y ), c_yellow, "!" );
7888 }
7889 bool is_npc = false;
7890 const monster *m = dynamic_cast<monster *>( critter );
7891 const npc *p = dynamic_cast<npc *>( critter );
7892 nc_color name_color = critter->basic_symbol_color();
7893
7894 if( selected ) {
7895 name_color = hilite( name_color );
7896 }
7897
7898 if( m != nullptr ) {
7899 trim_and_print( w_monsters, point( 1, y ), width - 26, name_color, m->name() );
7900 } else {
7901 trim_and_print( w_monsters, point( 1, y ), width - 26, name_color, critter->disp_name() );
7902 is_npc = true;
7903 }
7904
7905 if( selected && !get_safemode().empty() ) {
7906 const std::string monName = is_npc ? get_safemode().npc_type_name() : m->name();
7907
7908 std::string sSafemode;
7909 if( get_safemode().has_rule( monName, Creature::A_ANY ) ) {
7910 sSafemode = _( "<R>emove from safemode Blacklist" );
7911 } else {
7912 sSafemode = _( "<A>dd to safemode Blacklist" );
7913 }
7914
7915 shortcut_print( w_monsters, point( 2, getmaxy( w_monsters ) - 1 ),
7916 c_white, c_light_green, sSafemode );
7917 }
7918
7920 std::string sText;
7921
7922 if( m != nullptr ) {
7923 m->get_HP_Bar( color, sText );
7924 } else {
7925 std::tie( sText, color ) =
7926 ::get_hp_bar( critter->get_hp(), critter->get_hp_max(), false );
7927 }
7928 mvwprintz( w_monsters, point( width - 25, y ), color, sText );
7929
7930 if( m != nullptr ) {
7931 const auto att = m->get_attitude();
7932 sText = att.first;
7933 color = att.second;
7934 } else if( p != nullptr ) {
7935 sText = npc_attitude_name( p->get_attitude() );
7936 color = p->symbol_color();
7937 }
7938 mvwprintz( w_monsters, point( width - 19, y ), color, sText );
7939
7940 const int mon_dist = rl_dist( u.pos(), critter->pos() );
7941 const int numd = mon_dist > 999 ? 4 :
7942 mon_dist > 99 ? 3 :
7943 mon_dist > 9 ? 2 : 1;
7944
7945 trim_and_print( w_monsters, point( width - ( 8 + numd ), y ), 6 + numd,
7946 selected ? c_light_green : c_light_gray,
7947 "%*d %s",
7948 numd, mon_dist,
7949 direction_name_short( direction_from( u.pos(), critter->pos() ) ) );
7950 }
7951
7952 mvwprintz( w_monsters_border, point( ( width / 2 ) - numw - 2, 0 ), c_light_green, " %*d", numw,
7953 iActive + 1 );
7954 wprintz( w_monsters_border, c_white, " / %*d ", numw, static_cast<int>( monster_list.size() ) );
7955
7956 werase( w_monster_info );
7957 if( cCurMon ) {
7958 cCurMon->print_info( w_monster_info, 1, iInfoHeight - 3, 1 );
7959 }
7960
7961 draw_custom_border( w_monster_info_border, true, true, true, true, LINE_XXXO, LINE_XOXX, true,
7962 true );
7963
7964 if( bVMonsterLookFire ) {
7965 mvwprintw( w_monster_info_border, point_east, "< " );
7966 wprintz( w_monster_info_border, c_light_green, ctxt.press_x( "look" ) );
7967 wprintz( w_monster_info_border, c_light_gray, " %s", _( "to look around" ) );
7968
7969 if( cCurMon && rl_dist( u.pos(), cCurMon->pos() ) <= max_gun_range ) {
7970 wprintw( w_monster_info_border, " " );
7971 wprintz( w_monster_info_border, c_light_green, ctxt.press_x( "fire" ) );
7972 wprintz( w_monster_info_border, c_light_gray, " %s", _( "to shoot" ) );
7973 }
7974 wprintw( w_monster_info_border, " >" );
7975 }
7976
7977 draw_scrollbar( w_monsters_border, iActive, iMaxRows, static_cast<int>( monster_list.size() ),
7978 point_south );
7979 }
7980
7981 wnoutrefresh( w_monsters_border );
7982 wnoutrefresh( w_monster_info_border );
7983 wnoutrefresh( w_monsters );
7984 wnoutrefresh( w_monster_info );
7985 }
7986 } );
7987
7988 std::optional<tripoint> trail_start;
7989 std::optional<tripoint> trail_end;
7990 bool trail_end_x = false;
7991 shared_ptr_fast<draw_callback_t> trail_cb = create_trail_callback( trail_start, trail_end,
7992 trail_end_x );
7993 add_draw_callback( trail_cb );
7994
7995 do {
7996 if( action == "UP" ) {
7997 iActive--;
7998 if( iActive < 0 ) {
7999 if( monster_list.empty() ) {
8000 iActive = 0;
8001 } else {
8002 iActive = static_cast<int>( monster_list.size() ) - 1;
8003 }
8004 }
8005 } else if( action == "DOWN" ) {
8006 iActive++;
8007 if( iActive >= static_cast<int>( monster_list.size() ) ) {
8008 iActive = 0;
8009 }
8010 } else if( action == "NEXT_TAB" || action == "PREV_TAB" ) {
8011 u.view_offset = stored_view_offset;
8013 } else if( action == "SAFEMODE_BLACKLIST_REMOVE" ) {
8014 const auto m = dynamic_cast<monster *>( cCurMon );
8015 const std::string monName = ( m != nullptr ) ? m->name() : "human";
8016
8017 if( get_safemode().has_rule( monName, Creature::A_ANY ) ) {
8019 }
8020 } else if( action == "SAFEMODE_BLACKLIST_ADD" ) {
8021 if( !get_safemode().empty() ) {
8022 const auto m = dynamic_cast<monster *>( cCurMon );
8023 const std::string monName = ( m != nullptr ) ? m->name() : "human";
8024
8025 get_safemode().add_rule( monName, Creature::A_ANY, get_option<int>( "SAFEMODEPROXIMITY" ),
8027 }
8028 } else if( action == "look" ) {
8029 hide_ui = true;
8030 ui.mark_resize();
8031 look_around();
8032 hide_ui = false;
8033 ui.mark_resize();
8034 } else if( action == "fire" ) {
8035 if( cCurMon != nullptr && rl_dist( u.pos(), cCurMon->pos() ) <= max_gun_range ) {
8036 u.last_target = shared_from( *cCurMon );
8037 add_msg( "Target_set" );
8039 u.view_offset = stored_view_offset;
8040 return game::vmenu_ret::FIRE;
8041 }
8042 }
8043
8044 if( iActive >= 0 && static_cast<size_t>( iActive ) < monster_list.size() ) {
8045 cCurMon = monster_list[iActive];
8046 iActivePos = cCurMon->pos() - u.pos();
8047 centerlistview( iActivePos, width );
8048 trail_start = u.pos();
8049 trail_end = cCurMon->pos();
8050 // Actually accessed from the terrain overlay callback `trail_cb` in the
8051 // call to `ui_manager::redraw`.
8052 //NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
8053 trail_end_x = false;
8054 } else {
8055 cCurMon = nullptr;
8056 iActivePos = tripoint_zero;
8057 u.view_offset = stored_view_offset;
8058 trail_start = trail_end = std::nullopt;
8059 }
8061
8063
8064 action = ctxt.handle_input();
8065 } while( action != "QUIT" );
8066
8067 u.view_offset = stored_view_offset;
8068
8069 return game::vmenu_ret::QUIT;
8070}
double recoil
Definition: character.h:571
nc_color symbol_color() const override
Definition: character.cpp:6042
static const std::pair< translation, nc_color > & get_attitude_ui_data(Attitude att)
Creature Attitude as String and color.
Definition: creature.cpp:1920
virtual const tripoint & pos() const =0
virtual int print_info(const catacurses::window &w, int vStart, int vLines, int column) const =0
Write information about this creature.
shared_ptr_fast< T > shared_from(const T &critter)
Returns a shared pointer to the given critter (which can be of any of the subclasses of Creature).
Definition: game.cpp:4593
bool bVMonsterLookFire
Definition: game.h:1034
int gun_range(const player *p) const
The weapons range in map squares.
Definition: item.cpp:7375
npc_attitude get_attitude() const
Definition: npc.cpp:3164
weak_ptr_fast< Creature > last_target
Definition: player.h:241
bool has_rule(const std::string &rule_in, Creature::Attitude attitude_in)
void remove_rule(const std::string &rule_in, Creature::Attitude attitude_in)
static nc_color color(const T_t &t)
@ RULE_BLACKLISTED
Definition: enums.h:54
constexpr double MAX_RECOIL
std::string npc_attitude_name(npc_attitude att)
Definition: npc.cpp:2568
std::pair< std::string, nc_color > get_hp_bar(const int cur_hp, const int max_hp, const bool is_mon)
Definition: output.cpp:1604
size_t shortcut_print(const catacurses::window &w, point p, nc_color text_color, nc_color shortcut_color, const std::string &fmt)
Definition: output.cpp:1543

References _, Creature::A_ANY, action, add_draw_callback(), add_msg(), safemode::add_rule(), bVMonsterLookFire, c_light_gray, c_light_green, c_magenta, c_white, c_yellow, calcStartPos(), centerlistview(), CHANGE_TAB, color(), create_trail_callback(), direction_from(), direction_name_short(), draw_custom_border(), draw_scrollbar(), FIRE, g, npc::get_attitude(), Creature::get_attitude_ui_data(), get_hp_bar(), get_safemode(), catacurses::getmaxy(), item::gun_range(), input_context::handle_input(), safemode::has_rule(), hilite(), invalidate_main_ui_adaptor(), player::last_target, LINE_XOXO, LINE_XOXX, LINE_XXXO, look_around(), m, MAX_RECOIL, catacurses::mvwprintw(), mvwprintz(), map::name(), catacurses::newwin(), npc_attitude_name(), safemode::npc_type_name(), point_east, point_south, point_zero, Creature::pos(), Character::pos(), input_context::press_x(), Character::primary_weapon(), Creature::print_info(), QUIT, Character::recoil, ui_manager::redraw(), input_context::register_action(), safemode::remove_rule(), rl_dist(), RULE_BLACKLISTED, shared_from(), shortcut_print(), Character::symbol_color(), TERMX, TERMY, to_translation(), trim_and_print(), tripoint_zero, u, player::view_offset, catacurses::werase(), catacurses::wnoutrefresh(), catacurses::wprintw(), and wprintz().

Referenced by list_items_monsters().

◆ load() [1/2]

bool game::load ( const save_t name)
private

Definition at line 2541 of file game.cpp.

2542{
2545 popup.message( "%s", _( "Please wait…\nLoading the save…" ) );
2548
2549 using namespace std::placeholders;
2550
2551 const std::string worldpath = get_world_base_save_path() + "/";
2552 const std::string playerpath = worldpath + name.base_path();
2553
2554 // Now load up the master game data; factions (and more?)
2555 load_master();
2556 u = avatar();
2557 u.set_save_id( name.decoded_name() );
2558 u.name = name.decoded_name();
2559 if( !read_from_file( playerpath + SAVE_EXTENSION, std::bind( &game::unserialize, this, _1 ) ) ) {
2560 return false;
2561 }
2562
2564 u.get_avatar_diary()->load();
2565
2567
2568 read_from_file_optional( worldpath + name.base_path() + SAVE_EXTENSION_LOG,
2569 std::bind( &memorial_logger::load, &memorial(), _1 ) );
2570
2571#if defined(__ANDROID__)
2572 read_from_file_optional( worldpath + name.base_path() + SAVE_EXTENSION_SHORTCUTS,
2573 std::bind( &game::load_shortcuts, this, _1 ) );
2574#endif
2575
2576 // Now that the player's worn items are updated, their sight limits need to be
2577 // recalculated. (This would be cleaner if u.worn were private.)
2579
2580 if( !gamemode ) {
2581 gamemode = std::make_unique<special_game>();
2582 }
2583
2584 safe_mode = get_option<bool>( "SAFEMODE" ) ? SAFE_MODE_ON : SAFE_MODE_OFF;
2585 mostseen = 0; // ...and mostseen is 0, we haven't seen any monsters yet.
2586
2587 init_autosave();
2588 get_auto_pickup().load_character(); // Load character auto pickup rules
2589 get_auto_notes_settings().load(); // Load character auto notes settings
2590 get_safemode().load_character(); // Load character safemode rules
2591 zone_manager::get_manager().load_zones(); // Load character world zones
2592 read_from_file_optional( get_world_base_save_path() + "/uistate.json", []( std::istream & stream ) {
2593 JsonIn jsin( stream );
2594 uistate.deserialize( jsin );
2595 } );
2596 reload_npcs();
2601 update_map( u );
2602 for( auto &e : u.inv_dump() ) {
2603 e->set_owner( g->u );
2604 }
2605 // legacy, needs to be here as we access the map.
2606 if( !u.getID().is_valid() ) {
2607 // player does not have a real id, so assign a new one,
2608 u.setID( assign_npc_id() );
2609 // The vehicle stores the IDs of the boarded players, so update it, too.
2610 if( u.in_vehicle ) {
2611 if( const std::optional<vpart_reference> vp = m.veh_at(
2612 u.pos() ).part_with_feature( "BOARDABLE", true ) ) {
2613 vp->part().passenger_id = u.getID();
2614 }
2615 }
2616 }
2617
2618 // populate calendar caches now, after active world is set, but before we do
2619 // anything else, to ensure they pick up the correct value from the save's
2620 // worldoptions
2621 calendar::set_eternal_season( ::get_option<bool>( "ETERNAL_SEASON" ) );
2622 calendar::set_season_length( ::get_option<int>( "SEASON_LENGTH" ) );
2623
2624 u.reset();
2625
2627
2629
2630 return true;
2631}
bool read_from_file(const std::string &path, const std::function< void(std::istream &)> &reader)
Try to open and read from given file using the given callback.
bool read_from_file_optional(const std::string &path, const std::function< void(std::istream &)> &reader)
void setID(character_id i, bool force=false)
Definition: character.cpp:484
std::vector< item * > inv_dump()
Definition: character.cpp:8962
void recalc_sight_limits()
Modifies the player's sight values Must be called when any of the following change: This must be call...
Definition: character.cpp:1630
void reset() override
Handles stat and bonus reset.
Definition: character.cpp:3646
Definition: json.h:172
Definition: avatar.h:55
void set_save_id(const std::string &id)
Definition: avatar.h:91
void load_map_memory()
Definition: avatar.cpp:138
Helper class that fills the background and obscures all UIs below.
Definition: ui_manager.h:193
bool is_valid() const
Definition: character_id.h:19
void load()
Definition: diary.cpp:810
void validate_linked_vehicles()
validate towed vehicles so they get linked up again after a load
Definition: game.cpp:1895
void reload_npcs()
Unloads, then loads the NPCs.
Definition: game.cpp:880
void validate_camps()
validate camps to ensure they are on the overmap list
Definition: game.cpp:1953
void load_master()
Definition: game.cpp:2510
void validate_mounted_npcs()
Definition: game.cpp:1910
character_id assign_npc_id()
Definition: game.cpp:3582
void unserialize(std::istream &fin)
Definition: savegame.cpp:167
void init_autosave()
Definition: game.cpp:11317
void validate_npc_followers()
validate list of followers to account for overmap buffers
Definition: game.cpp:1929
void load(std::istream &fin)
Loads the data in a memorial file from the given ifstream.
void load_character()
Create a popup on the UI stack that gets displayed but receives no input itself.
Definition: popup.h:278
void deserialize(const JsonObject &jo)
time_point nextweather
Definition: weather.h:205
void load_zones()
Definition: clzones.cpp:1217
static const std::string SAVE_EXTENSION(".sav")
static const std::string SAVE_EXTENSION_SHORTCUTS(".shortcuts")
static const std::string SAVE_EXTENSION_LOG(".log")
void set_season_length(int dur)
Definition: calendar.cpp:478
void set_eternal_season(bool is_eternal_season)
Definition: calendar.cpp:470
void run_on_game_load_hooks(lua_state &state)
Definition: catalua.cpp:420
bool load_world_lua_state(const std::string &)
Definition: catalua.cpp:69

References _, assign_npc_id(), uistatedata::deserialize(), g, gamemode, get_auto_notes_settings(), get_auto_pickup(), avatar::get_avatar_diary(), DynamicDataLoader::get_instance(), zone_manager::get_manager(), get_safemode(), get_weather, get_world_base_save_path(), Character::getID(), Character::in_vehicle, init_autosave(), Character::inv_dump(), character_id::is_valid(), auto_notes::auto_note_settings::load(), diary::load(), memorial_logger::load(), auto_pickup::player_settings::load_character(), safemode::load_character(), avatar::load_map_memory(), load_master(), cata::load_world_lua_state(), zone_manager::load_zones(), m, memorial(), mostseen, Character::name, om_direction::name(), weather_manager::nextweather, optional_vpart_position::part_with_feature(), popup(), Character::pos(), read_from_file(), read_from_file_optional(), Character::recalc_sight_limits(), ui_manager::redraw(), refresh_display(), reload_npcs(), Character::reset(), cata::run_on_game_load_hooks(), safe_mode, SAFE_MODE_OFF, SAFE_MODE_ON, SAVE_EXTENSION(), SAVE_EXTENSION_LOG(), SAVE_EXTENSION_SHORTCUTS(), calendar::set_eternal_season(), avatar::set_save_id(), calendar::set_season_length(), Character::setID(), calendar::turn, u, uistate, unserialize(), update_map(), validate_camps(), validate_linked_vehicles(), validate_mounted_npcs(), validate_npc_followers(), and map::veh_at().

◆ load() [2/2]

bool game::load ( const std::string &  world)

Attempt to load first valid save (if any) in world.

Definition at line 2517 of file game.cpp.

2518{
2519 world_generator->init();
2520 const WORLDPTR wptr = world_generator->get_world( world );
2521 if( !wptr ) {
2522 return false;
2523 }
2524 if( wptr->world_saves.empty() ) {
2525 debugmsg( "world '%s' contains no saves", world );
2526 return false;
2527 }
2528
2529 try {
2530 world_generator->set_active_world( wptr );
2531 g->setup();
2532 g->load( wptr->world_saves.front() );
2533 } catch( const std::exception &err ) {
2534 debugmsg( "cannot load world '%s': %s", world, err.what() );
2535 return false;
2536 }
2537
2538 return true;
2539}
std::vector< save_t > world_saves
Definition: worldfactory.h:62

References debugmsg, g, world_generator, and WORLD::world_saves.

Referenced by quickload().

◆ load_map() [1/2]

void game::load_map ( const tripoint pos_sm,
bool  pump_events = false 
)

Load the main map at given location, see map::load, in global, absolute submap coordinates.

Parameters
pump_eventsIf true, handle window events during loading. If you set this to true, do ensure that the map is not accessed before this function returns (for example, UIs that draw the map should be disabled).

Definition at line 544 of file game.cpp.

545{
546 // TODO: fix point types
547 load_map( tripoint_abs_sm( pos_sm ), pump_events );
548}
void load_map(const tripoint &pos_sm, bool pump_events=false)
Load the main map at given location, see map::load, in global, absolute submap coordinates.
Definition: game.cpp:544
coords::coord_point< tripoint, coords::origin::abs, coords::sm > tripoint_abs_sm
Definition: coordinates.h:490

References load_map().

Referenced by load_map(), place_player_overmap(), start_game(), and unserialize().

◆ load_map() [2/2]

void game::load_map ( const tripoint_abs_sm pos_sm,
bool  pump_events = false 
)

Definition at line 550 of file game.cpp.

552{
553 m.load( pos_sm, true, pump_events );
554 grid_tracker_ptr->load( m );
555}
void load(const tripoint &w, bool update_vehicles, bool pump_events=false)
Load submaps into grid.
Definition: map.cpp:6750

References grid_tracker_ptr, map::load(), and m.

◆ load_master()

void game::load_master ( )
private

Definition at line 2510 of file game.cpp.

2511{
2512 using namespace std::placeholders;
2513 const auto datafile = get_world_base_save_path() + "/" + SAVE_MASTER;
2514 read_from_file_optional( datafile, std::bind( &game::unserialize_master, this, _1 ) );
2515}
void unserialize_master(std::istream &fin)
Definition: savegame.cpp:1193
static const std::string SAVE_MASTER("master.gsav")

References get_world_base_save_path(), read_from_file_optional(), SAVE_MASTER(), and unserialize_master().

Referenced by load(), and start_game().

◆ load_npcs()

void game::load_npcs ( )

Makes any nearby NPCs on the overmap active.

Definition at line 818 of file game.cpp.

819{
820 const int radius = HALF_MAPSIZE - 1;
821 // uses submap coordinates
822 std::vector<shared_ptr_fast<npc>> just_added;
823 for( const auto &temp : overmap_buffer.get_npcs_near_player( radius ) ) {
824 const character_id &id = temp->getID();
825 const auto found = std::find_if( active_npc.begin(), active_npc.end(),
826 [id]( const shared_ptr_fast<npc> &n ) {
827 return n->getID() == id;
828 } );
829 if( found != active_npc.end() ) {
830 continue;
831 }
832 if( temp->is_active() ) {
833 continue;
834 }
835 if( temp->has_companion_mission() ) {
836 continue;
837 }
838
839 const tripoint sm_loc = temp->global_sm_location();
840 // NPCs who are out of bounds before placement would be pushed into bounds
841 // This can cause NPCs to teleport around, so we don't want that
842 if( sm_loc.x < get_levx() || sm_loc.x >= get_levx() + MAPSIZE ||
843 sm_loc.y < get_levy() || sm_loc.y >= get_levy() + MAPSIZE ||
844 ( sm_loc.z != get_levz() && !m.has_zlevels() ) ) {
845 continue;
846 }
847
848 add_msg( m_debug, "game::load_npcs: Spawning static NPC, %d:%d:%d (%d:%d:%d)",
849 get_levx(), get_levy(), get_levz(), sm_loc.x, sm_loc.y, sm_loc.z );
850 temp->place_on_map();
851 if( !m.inbounds( temp->pos() ) ) {
852 continue;
853 }
854 // In the rare case the npc was marked for death while
855 // it was on the overmap. Kill it.
856 if( temp->marked_for_death ) {
857 temp->die( nullptr );
858 } else {
859 active_npc.push_back( temp );
860 just_added.push_back( temp );
861 }
862 }
863
864 for( const auto &npc : just_added ) {
865 npc->on_load();
866 }
867
868 npcs_dirty = false;
869}
void on_load()
Retroactively update npc.
Definition: npc.cpp:2681
static constexpr int MAPSIZE

References active_npc, add_msg(), get_levx(), get_levy(), get_levz(), overmapbuffer::get_npcs_near_player(), HALF_MAPSIZE, map::has_zlevels(), map::inbounds(), m, m_debug, MAPSIZE, npcs_dirty, npc::on_load(), overmap_buffer, tripoint::x, tripoint::y, and tripoint::z.

Referenced by do_turn(), perhaps_add_random_npc(), place_player_overmap(), reload_npcs(), save_cyborg(), spawn_hallucination(), start_game(), and update_map().

◆ load_static_data()

void game::load_static_data ( )

Loads static data that does not depend on mods or similar.

Definition at line 340 of file game.cpp.

341{
342 // UI stuff, not mod-specific per definition
343 inp_mngr.init(); // Load input config JSON
344 // Init mappings for loading the json stuff
346 fullscreen = false;
347 was_fullscreen = false;
348 show_panel_adm = false;
350
351 // These functions do not load stuff from json.
352 // The content they load/initialize is hardcoded into the program.
353 // Therefore they can be loaded here.
354 // If this changes (if they load data from json), they have to
355 // be moved to game::load_mod
356
360}
bool was_fullscreen
Definition: game.h:1016
bool fullscreen
Definition: game.h:1015
void init()
Initializes the input manager, aka loads the input mapping configuration JSON.
Definition: input.cpp:111
void init()
Definition: panels.cpp:2203
void load_global()

References fullscreen, get_auto_pickup(), get_distraction_manager(), DynamicDataLoader::get_instance(), panel_manager::get_manager(), get_safemode(), input_manager::init(), panel_manager::init(), inp_mngr, distraction_manager::distraction_manager_gui::load(), auto_pickup::player_settings::load_global(), safemode::load_global(), show_panel_adm, and was_fullscreen.

◆ look_around() [1/2]

std::optional< tripoint > game::look_around ( bool  force_3d = false)

Definition at line 6600 of file game.cpp.

6601{
6603 look_around_result result = look_around( /*show_window=*/true, center, center, false, false,
6604 false, false, tripoint_zero, force_3d );
6605 return result.position;
6606}

References center, look_around(), Character::pos(), tripoint_zero, u, and player::view_offset.

Referenced by chat(), handle_action(), list_monsters(), look_around(), peek(), and zones_manager().

◆ look_around() [2/2]

look_around_result game::look_around ( bool  show_window,
tripoint center,
const tripoint start_point,
bool  has_first_point,
bool  select_zone,
bool  peeking,
bool  is_moving_zone = false,
const tripoint end_point = tripoint_zero,
bool  force_3d = false 
)
Parameters
show_windowdisplay the info window that holds the tile information in the position.
centerused to calculate the u.view_offset, could center the screen to the position it represents
start_pointthe start point of the targeting zone, also the initial local position of the cursor
has_first_pointshould be true if the first point has been selected when editing the zone
select_zonetrue if the zone is being edited
peekingdetermines if the player is peeking
is_moving_zonetrue if the zone is being moved, false by default
end_pointthe end point of the targeting zone, only used if is_moving_zone is true, default is tripoint_zero
Returns
look_around_result

Definition at line 6608 of file game.cpp.

6611{
6612 bVMonsterLookFire = false;
6613 // TODO: Make this `true`
6614 const bool allow_zlev_move = m.has_zlevels() && ( get_option<bool>( "FOV_3D" ) || force_3d );
6615
6617
6618 tripoint lp = is_moving_zone ? ( start_point + end_point ) / 2 : start_point; // cursor
6619 int &lx = lp.x;
6620 int &ly = lp.y;
6621 int &lz = lp.z;
6622
6623 int soffset = get_option<int>( "FAST_SCROLL_OFFSET" );
6624 bool fast_scroll = false;
6625
6626 std::unique_ptr<ui_adaptor> ui;
6627 catacurses::window w_info;
6628 if( show_window ) {
6629 ui = std::make_unique<ui_adaptor>();
6630 ui->on_screen_resize( [&]( ui_adaptor & ui ) {
6631 int panel_width = panel_manager::get_manager().get_current_layout().begin()->get_width();
6633
6634 // If particularly small, base height on panel width irrespective of other elements.
6635 // Value here is attempting to get a square-ish result assuming 1x2 proportioned font.
6636 if( height < panel_width / 2 ) {
6637 height = panel_width / 2;
6638 }
6639
6640 int la_y = 0;
6641 int la_x = TERMX - panel_width;
6642 std::string position = get_option<std::string>( "LOOKAROUND_POSITION" );
6643 if( position == "left" ) {
6644 if( get_option<std::string>( "SIDEBAR_POSITION" ) == "right" ) {
6646 } else {
6647 la_x = panel_manager::get_manager().get_width_left() - panel_width;
6648 }
6649 }
6650 int la_h = height;
6651 int la_w = panel_width;
6652 w_info = catacurses::newwin( la_h, la_w, point( la_x, la_y ) );
6653
6654 ui.position_from_window( w_info );
6655 } );
6656 ui->mark_resize();
6657 }
6658
6659 std::string action;
6660 input_context ctxt( "LOOK" );
6661 ctxt.set_iso( true );
6662 ctxt.register_directions();
6663 ctxt.register_action( "COORDINATE" );
6664 ctxt.register_action( "LEVEL_UP" );
6665 ctxt.register_action( "LEVEL_DOWN" );
6666 ctxt.register_action( "TOGGLE_FAST_SCROLL" );
6667 ctxt.register_action( "EXTENDED_DESCRIPTION" );
6668 ctxt.register_action( "SELECT" );
6669 if( peeking ) {
6670 ctxt.register_action( "throw_blind" );
6671 }
6672 if( !select_zone ) {
6673 ctxt.register_action( "TRAVEL_TO" );
6674 ctxt.register_action( "LIST_ITEMS" );
6675 }
6676 ctxt.register_action( "MOUSE_MOVE" );
6677 ctxt.register_action( "CENTER" );
6678
6679 ctxt.register_action( "debug_scent" );
6680 ctxt.register_action( "debug_scent_type" );
6681 ctxt.register_action( "debug_temp" );
6682 ctxt.register_action( "debug_visibility" );
6683 ctxt.register_action( "debug_lighting" );
6684 ctxt.register_action( "debug_radiation" );
6685 ctxt.register_action( "debug_submap_grid" );
6686 ctxt.register_action( "debug_hour_timer" );
6687 ctxt.register_action( "CONFIRM" );
6688 ctxt.register_action( "QUIT" );
6689 ctxt.register_action( "HELP_KEYBINDINGS" );
6690 if( use_tiles ) {
6691 ctxt.register_action( "zoom_out" );
6692 ctxt.register_action( "zoom_in" );
6693 }
6694#if defined(TILES)
6695 ctxt.register_action( "toggle_pixel_minimap" );
6696#endif // TILES
6697
6698 const int old_levz = get_levz();
6699 const int min_levz = force_3d ? -OVERMAP_DEPTH : std::max( old_levz - fov_3d_z_range,
6700 -OVERMAP_DEPTH );
6701 const int max_levz = force_3d ? OVERMAP_HEIGHT : std::min( old_levz + fov_3d_z_range,
6703
6704 m.update_visibility_cache( old_levz );
6706
6707 bool blink = true;
6709
6710 shared_ptr_fast<draw_callback_t> ter_indicator_cb;
6711
6712 if( show_window && ui ) {
6713 ui->on_redraw( [&]( const ui_adaptor & ) {
6714 werase( w_info );
6715 draw_border( w_info );
6716
6717 center_print( w_info, 0, c_white, string_format( _( "< <color_green>Look Around</color> >" ) ) );
6718
6719 std::string extended_descr_text = string_format( _( "%s - %s" ),
6720 ctxt.get_desc( "EXTENDED_DESCRIPTION" ),
6721 ctxt.get_action_name( "EXTENDED_DESCRIPTION" ) );
6722 std::string fast_scroll_text = string_format( _( "%s - %s" ),
6723 ctxt.get_desc( "TOGGLE_FAST_SCROLL" ),
6724 ctxt.get_action_name( "TOGGLE_FAST_SCROLL" ) );
6725#if defined(TILES)
6726 std::string pixel_minimap_text = string_format( _( "%s - %s" ),
6727 ctxt.get_desc( "toggle_pixel_minimap" ),
6728 ctxt.get_action_name( "toggle_pixel_minimap" ) );
6729#endif // TILES
6730
6731 center_print( w_info, getmaxy( w_info ) - 2, c_light_gray, extended_descr_text );
6732 mvwprintz( w_info, point( 1, getmaxy( w_info ) - 1 ), fast_scroll ? c_light_green : c_green,
6733 fast_scroll_text );
6734#if defined(TILES)
6735 right_print( w_info, getmaxy( w_info ) - 1, 1, pixel_minimap_option ? c_light_green : c_green,
6736 pixel_minimap_text );
6737#endif // TILES
6738
6739 int first_line = 1;
6740 const int last_line = getmaxy( w_info ) - 3;
6741 pre_print_all_tile_info( lp, w_info, first_line, last_line, cache );
6742
6743 wnoutrefresh( w_info );
6744 } );
6745 ter_indicator_cb = make_shared_fast<draw_callback_t>( [&]() {
6746 draw_look_around_cursor( lp, cache );
6747 } );
6748 add_draw_callback( ter_indicator_cb );
6749 }
6750
6751 std::optional<tripoint> zone_start;
6752 std::optional<tripoint> zone_end;
6753 bool zone_blink = false;
6754 bool zone_cursor = true;
6755 shared_ptr_fast<draw_callback_t> zone_cb = create_zone_callback( zone_start, zone_end, zone_blink,
6756 zone_cursor, is_moving_zone );
6757 add_draw_callback( zone_cb );
6758
6759 is_looking = true;
6760 const tripoint prev_offset = u.view_offset;
6761#if defined(TILES)
6762 const int prev_tileset_zoom = tileset_zoom;
6763 while( is_moving_zone && square_dist( start_point, end_point ) > 256 / get_zoom() &&
6764 get_zoom() != 4 ) {
6765 zoom_out();
6766 }
6768#endif
6769 do {
6770 u.view_offset = center - u.pos();
6771 if( select_zone ) {
6772 if( has_first_point ) {
6773 zone_start = start_point;
6774 zone_end = lp;
6775 } else {
6776 zone_start = lp;
6777 zone_end = std::nullopt;
6778 }
6779 // Actually accessed from the terrain overlay callback `zone_cb` in the
6780 // call to `ui_manager::redraw`.
6781 //NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
6782 zone_blink = blink;
6783 }
6784
6785 if( is_moving_zone ) {
6786 zone_start = lp - ( start_point + end_point ) / 2 + start_point;
6787 zone_end = lp - ( start_point + end_point ) / 2 + end_point;
6788 // Actually accessed from the terrain overlay callback `zone_cb` in the
6789 // call to `ui_manager::redraw`.
6790 //NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
6791 zone_blink = blink;
6792 }
6795 if( ( select_zone && has_first_point ) || is_moving_zone ) {
6796 ctxt.set_timeout( get_option<int>( "BLINK_SPEED" ) );
6797 }
6798
6799 //Wait for input
6800 // only specify a timeout here if "EDGE_SCROLL" is enabled
6801 // otherwise use the previously set timeout
6802 const tripoint edge_scroll = mouse_edge_scrolling_terrain( ctxt );
6803 const int scroll_timeout = get_option<int>( "EDGE_SCROLL" );
6804 const bool edge_scrolling = edge_scroll != tripoint_zero && scroll_timeout >= 0;
6805 if( edge_scrolling ) {
6806 action = ctxt.handle_input( scroll_timeout );
6807 } else {
6808 action = ctxt.handle_input();
6809 }
6810 if( ( action == "LEVEL_UP" || action == "LEVEL_DOWN" || action == "MOUSE_MOVE" ||
6811 ctxt.get_direction( action ) ) && ( ( select_zone && has_first_point ) || is_moving_zone ) ) {
6812 blink = true; // Always draw blink symbols when moving cursor
6813 } else if( action == "TIMEOUT" ) {
6814 blink = !blink;
6815 }
6816 if( action == "LIST_ITEMS" ) {
6818 } else if( action == "TOGGLE_FAST_SCROLL" ) {
6819 fast_scroll = !fast_scroll;
6820 } else if( action == "toggle_pixel_minimap" ) {
6822
6823 if( show_window && ui ) {
6824 ui->mark_resize();
6825 }
6826 } else if( action == "LEVEL_UP" || action == "LEVEL_DOWN" ) {
6827 if( !allow_zlev_move ) {
6828 continue;
6829 }
6830
6831 const int dz = ( action == "LEVEL_UP" ? 1 : -1 );
6832 lz = clamp( lz + dz, min_levz, max_levz );
6833 center.z = clamp( center.z + dz, min_levz, max_levz );
6834
6835 add_msg( m_debug, "levx: %d, levy: %d, levz: %d", get_levx(), get_levy(), center.z );
6836 u.view_offset.z = center.z - u.posz();
6838 } else if( action == "TRAVEL_TO" ) {
6839 if( !u.sees( lp ) ) {
6840 add_msg( _( "You can't see that destination." ) );
6841 continue;
6842 }
6843
6844 auto route = m.route( u.pos(), lp, u.get_pathfinding_settings(), u.get_path_avoid() );
6845 if( route.size() > 1 ) {
6846 route.pop_back();
6847 u.set_destination( route );
6848 } else {
6849 add_msg( m_info, _( "You can't travel there." ) );
6850 continue;
6851 }
6852 } else if( action == "debug_scent" || action == "debug_scent_type" ) {
6854 display_scent();
6855 }
6856 } else if( action == "debug_temp" ) {
6859 }
6860 } else if( action == "debug_lighting" ) {
6863 }
6864 } else if( action == "debug_transparency" ) {
6867 }
6868 } else if( action == "debug_radiation" ) {
6871 }
6872 } else if( action == "debug_submap_grid" ) {
6873 g->debug_submap_grid_overlay = !g->debug_submap_grid_overlay;
6874 } else if( action == "debug_hour_timer" ) {
6876 } else if( action == "EXTENDED_DESCRIPTION" ) {
6878 } else if( action == "CENTER" ) {
6879 center = u.pos();
6880 lp = u.pos();
6881 u.view_offset.z = 0;
6882 } else if( action == "MOUSE_MOVE" || action == "TIMEOUT" ) {
6883 // This block is structured this way so that edge scroll can work
6884 // whether the mouse is moving at the edge or simply stationary
6885 // at the edge. But even if edge scroll isn't in play, there's
6886 // other things for us to do here.
6887
6888 if( edge_scrolling ) {
6889 center += action == "MOUSE_MOVE" ? edge_scroll * 2 : edge_scroll;
6890 } else if( action == "MOUSE_MOVE" ) {
6891 const std::optional<tripoint> mouse_pos = ctxt.get_coordinates( w_terrain );
6892 if( mouse_pos ) {
6893 lx = mouse_pos->x;
6894 ly = mouse_pos->y;
6895 }
6896 }
6897 } else if( std::optional<tripoint> vec = ctxt.get_direction( action ) ) {
6898 if( fast_scroll ) {
6899 vec->x *= soffset;
6900 vec->y *= soffset;
6901 }
6902
6903 lx = lx + vec->x;
6904 ly = ly + vec->y;
6905 center.x = center.x + vec->x;
6906 center.y = center.y + vec->y;
6907 } else if( action == "throw_blind" ) {
6908 result.peek_action = PA_BLIND_THROW;
6909 } else if( action == "zoom_in" ) {
6910 center.x = lp.x;
6911 center.y = lp.y;
6912 zoom_in();
6914 } else if( action == "zoom_out" ) {
6915 center.x = lp.x;
6916 center.y = lp.y;
6917 zoom_out();
6919 }
6920 } while( action != "QUIT" && action != "CONFIRM" && action != "SELECT" && action != "TRAVEL_TO" &&
6921 action != "throw_blind" );
6922
6923 if( m.has_zlevels() && center.z != old_levz ) {
6924 m.invalidate_map_cache( old_levz );
6925 m.build_map_cache( old_levz );
6926 u.view_offset.z = 0;
6927 }
6928
6929 ctxt.reset_timeout();
6930 u.view_offset = prev_offset;
6931 zone_cb = nullptr;
6932 is_looking = false;
6933
6935 bVMonsterLookFire = true;
6936
6937 if( action == "CONFIRM" || action == "SELECT" ) {
6938 result.position = is_moving_zone ? zone_start : lp;
6939 }
6940
6941#if defined(TILES)
6942 if( is_moving_zone && get_zoom() != prev_tileset_zoom ) {
6943 // Reset the tileset zoom to the previous value
6944 set_zoom( prev_tileset_zoom );
6946 }
6947#endif
6948
6949 return result;
6950}
bool pixel_minimap_option
Whether to show the pixel minimap.
tripoint mouse_edge_scrolling_terrain(input_context &ctxt)
Used to implement mouse "edge scrolling".
Definition: game.cpp:2080
void set_zoom(int level)
Definition: game.cpp:7107
void draw_look_around_cursor(const tripoint &lp, const visibility_variables &cache)
Definition: game.cpp:5708
void extended_description(const tripoint &p)
Long description of (visible) things at tile.
void pre_print_all_tile_info(const tripoint &lp, const catacurses::window &w_info, int &line, int last_line, const visibility_variables &cache)
Definition: game.cpp:6587
int get_zoom() const
Definition: game.cpp:7119
const visibility_variables & get_visibility_variables_cache() const
Definition: map.cpp:5785
void invalidate_map_cache(const int zlev)
Definition: map.cpp:8970
std::vector< window_panel > & get_current_layout()
Definition: panels.cpp:2171
int square_dist(const coords::coord_point< Point, Origin, Scale > &loc1, const coords::coord_point< Point, Origin, Scale > &loc2)
Definition: coordinates.h:505
static shared_ptr_fast< game::draw_callback_t > create_zone_callback(const std::optional< tripoint > &zone_start, const std::optional< tripoint > &zone_end, const bool &zone_blink, const bool &zone_cursor, const bool &is_moving_zone=false)
Definition: game.cpp:3041
@ PA_BLIND_THROW
Definition: game.h:122
static constexpr int OVERMAP_HEIGHT
static constexpr int OVERMAP_DEPTH
int right_print(const catacurses::window &w, const int line, const int right_indent, const nc_color &FG, const std::string &text)
Definition: output.cpp:461

References _, action, add_draw_callback(), add_msg(), map::build_map_cache(), bVMonsterLookFire, c_green, c_light_gray, c_light_green, c_white, center, center_print(), clamp(), create_zone_callback(), display_lighting(), display_radiation(), display_scent(), display_temperature(), display_transparency(), draw_border(), draw_look_around_cursor(), extended_description(), fov_3d_z_range, g, input_context::get_action_name(), input_context::get_coordinates(), panel_manager::get_current_layout(), input_context::get_desc(), input_context::get_direction(), get_levx(), get_levy(), get_levz(), panel_manager::get_manager(), Character::get_path_avoid(), Character::get_pathfinding_settings(), map::get_visibility_variables_cache(), panel_manager::get_width_left(), get_zoom(), catacurses::getmaxy(), input_context::handle_input(), map::has_zlevels(), invalidate_main_ui_adaptor(), map::invalidate_map_cache(), is_looking, MAP_SHARING::isCompetitive(), MAP_SHARING::isDebugger(), list_items_monsters(), m, m_debug, m_info, mark_main_ui_adaptor_resize(), mouse_edge_scrolling_terrain(), mvwprintz(), catacurses::newwin(), OVERMAP_DEPTH, OVERMAP_HEIGHT, PA_BLIND_THROW, pixel_minimap_option, Character::pos(), Character::posz(), pre_print_all_tile_info(), ui_manager::redraw(), reenter_fullscreen(), input_context::register_action(), input_context::register_directions(), input_context::reset_timeout(), right_print(), map::route(), Character::sees(), Character::set_destination(), input_context::set_iso(), input_context::set_timeout(), set_zoom(), square_dist(), string_format(), temp_exit_fullscreen(), TERMX, TERMY, tileset_zoom, toggle_debug_hour_timer(), toggle_pixel_minimap(), tripoint_zero, u, map::update_visibility_cache(), use_tiles, player::view_offset, w_pixel_minimap, w_terrain, catacurses::werase(), catacurses::wnoutrefresh(), tripoint::x, tripoint::y, tripoint::z, zoom_in(), and zoom_out().

◆ look_debug()

std::optional< tripoint > game::look_debug ( )

Definition at line 5701 of file game.cpp.

5702{
5703 editmap edit;
5704 return edit.edit();
5705}
std::optional< tripoint > edit()
Definition: editmap.cpp:341

References editmap::edit().

◆ mark_main_ui_adaptor_resize()

void game::mark_main_ui_adaptor_resize ( ) const

Definition at line 2998 of file game.cpp.

2999{
3001 if( ui ) {
3002 ui->mark_resize();
3003 }
3004}

References main_ui_adaptor.

Referenced by handle_action(), look_around(), toggle_fullscreen(), and toggle_pixel_minimap().

◆ memorial()

memorial_logger & game::memorial ( )

Definition at line 2729 of file game.cpp.

2730{
2731 return *memorial_logger_ptr;
2732}

References memorial_logger_ptr.

Referenced by cleanup_at_end(), load(), save_player_data(), win(), win_screen(), and write_memorial_file().

◆ mon_info()

void game::mon_info ( const catacurses::window w,
int  hor_padding = 0 
)

Definition at line 3689 of file game.cpp.

3690{
3691 const monster_visible_info &mon_visible = u.get_mon_visible();
3692 const auto &unique_types = mon_visible.unique_types;
3693 const auto &unique_mons = mon_visible.unique_mons;
3694 const auto &dangerous = mon_visible.dangerous;
3695
3696 const int width = getmaxx( w ) - 2 * hor_padding;
3697 const int maxheight = getmaxy( w );
3698
3699 const int startrow = 0;
3700
3701 // Print the direction headings
3702 // Reminder:
3703 // 7 0 1 unique_types uses these indices;
3704 // 6 8 2 0-7 are provide by direction_from()
3705 // 5 4 3 8 is used for local monsters (for when we explain them below)
3706
3707 const std::array<std::string, 8> dir_labels = {{
3708 _( "North:" ), _( "NE:" ), _( "East:" ), _( "SE:" ),
3709 _( "South:" ), _( "SW:" ), _( "West:" ), _( "NW:" )
3710 }
3711 };
3712 std::array<int, 8> widths;
3713 for( int i = 0; i < 8; i++ ) {
3714 widths[i] = utf8_width( dir_labels[i] );
3715 }
3716 std::array<int, 8> xcoords;
3717 const std::array<int, 8> ycoords = {{ 0, 0, 1, 2, 2, 2, 1, 0 }};
3718 xcoords[0] = xcoords[4] = width / 3;
3719 xcoords[1] = xcoords[3] = xcoords[2] = ( width / 3 ) * 2;
3720 xcoords[5] = xcoords[6] = xcoords[7] = 0;
3721 //for the alignment of the 1,2,3 rows on the right edge
3722 xcoords[2] -= utf8_width( _( "East:" ) ) - utf8_width( _( "NE:" ) );
3723 for( int i = 0; i < 8; i++ ) {
3724 nc_color c = unique_types[i].empty() && unique_mons[i].empty() ? c_dark_gray
3725 : ( dangerous[i] ? c_light_red : c_light_gray );
3726 mvwprintz( w, point( xcoords[i] + hor_padding, ycoords[i] + startrow ), c, dir_labels[i] );
3727 }
3728
3729 // Print the symbols of all monsters in all directions.
3730 for( int i = 0; i < 8; i++ ) {
3731 point pr( xcoords[i] + widths[i] + 1, ycoords[i] + startrow );
3732
3733 // The list of symbols needs a space on each end.
3734 int symroom = ( width / 3 ) - widths[i] - 2;
3735 const int typeshere_npc = unique_types[i].size();
3736 const int typeshere_mon = unique_mons[i].size();
3737 const int typeshere = typeshere_mon + typeshere_npc;
3738 for( int j = 0; j < typeshere && j < symroom; j++ ) {
3739 nc_color c;
3740 std::string sym;
3741 if( symroom < typeshere && j == symroom - 1 ) {
3742 // We've run out of room!
3743 c = c_white;
3744 sym = "+";
3745 } else if( j < typeshere_npc ) {
3746 switch( unique_types[i][j]->get_attitude() ) {
3747 case NPCATT_KILL:
3748 c = c_red;
3749 break;
3750 case NPCATT_FOLLOW:
3751 c = c_light_green;
3752 break;
3753 default:
3754 c = c_pink;
3755 break;
3756 }
3757 sym = "@";
3758 } else {
3759 const mtype &mt = *unique_mons[i][j - typeshere_npc].first;
3760 c = mt.color;
3761 sym = mt.sym;
3762 }
3763 mvwprintz( w, pr, c, sym );
3764
3765 pr.x++;
3766 }
3767 }
3768
3769 // Now we print their full names!
3770 struct nearest_loc_and_cnt {
3771 int nearest_loc;
3772 int cnt;
3773 };
3774 std::map<const mtype *, nearest_loc_and_cnt> all_mons;
3775 for( int loc = 0; loc < 9; loc++ ) {
3776 for( const std::pair<const mtype *, int> &mon : unique_mons[loc] ) {
3777 const auto mon_it = all_mons.find( mon.first );
3778 if( mon_it == all_mons.end() ) {
3779 all_mons.emplace( mon.first, nearest_loc_and_cnt{ loc, mon.second } );
3780 } else {
3781 // 8 being the nearest location (local monsters)
3782 mon_it->second.nearest_loc = std::max( mon_it->second.nearest_loc, loc );
3783 mon_it->second.cnt += mon.second;
3784 }
3785 }
3786 }
3787 std::vector<std::pair<const mtype *, int>> mons_at[9];
3788 for( const std::pair<const mtype *const, nearest_loc_and_cnt> &mon : all_mons ) {
3789 mons_at[mon.second.nearest_loc].emplace_back( mon.first, mon.second.cnt );
3790 }
3791
3792 // Start printing monster names on row 4. Rows 0-2 are for labels, and row 3
3793 // is blank.
3794 point pr( hor_padding, 4 + startrow );
3795
3796 // Print monster names, starting with those at location 8 (nearby).
3797 for( int j = 8; j >= 0 && pr.y < maxheight; j-- ) {
3798 // Separate names by some number of spaces (more for local monsters).
3799 int namesep = ( j == 8 ? 2 : 1 );
3800 for( const std::pair<const mtype *, int> &mon : mons_at[j] ) {
3801 const mtype *const type = mon.first;
3802 const int count = mon.second;
3803 if( pr.y >= maxheight ) {
3804 // no space to print to anyway
3805 break;
3806 }
3807
3808 const mtype &mt = *type;
3809 std::string name = mt.nname( count );
3810 // Some languages don't have plural forms, but we want to always
3811 // omit 1.
3812 if( count != 1 ) {
3813 name = string_format( pgettext( "monster count and name", "%1$d %2$s" ),
3814 count, name );
3815 }
3816
3817 // Move to the next row if necessary. (The +2 is for the "Z ").
3818 if( pr.x + 2 + utf8_width( name ) >= width ) {
3819 pr.y++;
3820 pr.x = hor_padding;
3821 }
3822
3823 if( pr.y < maxheight ) { // Don't print if we've overflowed
3824 mvwprintz( w, pr, mt.color, mt.sym );
3825 pr.x += 2; // symbol and space
3826 nc_color danger = c_dark_gray;
3827 if( mt.difficulty >= 30 ) {
3828 danger = c_red;
3829 } else if( mt.difficulty >= 16 ) {
3830 danger = c_light_red;
3831 } else if( mt.difficulty >= 8 ) {
3832 danger = c_white;
3833 } else if( mt.agro > 0 ) {
3834 danger = c_light_gray;
3835 }
3836 mvwprintz( w, pr, danger, name );
3837 pr.x += utf8_width( name ) + namesep;
3838 }
3839 }
3840 }
3841}
@ NPCATT_KILL
Definition: npc.h:91
@ NPCATT_FOLLOW
Definition: npc.h:84
std::vector< std::pair< const mtype *, int > > unique_mons[9]
Definition: avatar.h:48
bool dangerous[8]
Definition: avatar.h:51
std::vector< npc * > unique_types[9]
Definition: avatar.h:47
Definition: mtype.h:208
std::string sym
UTF-8 encoded symbol, should be exactly one cell wide.
Definition: mtype.h:256
nc_color color
Definition: mtype.h:261
int difficulty
Definition: mtype.h:267
int agro
e.g.
Definition: mtype.h:272

References _, mtype::agro, c, c_dark_gray, c_light_gray, c_light_green, c_light_red, c_pink, c_red, c_white, mtype::color, detail::count(), monster_visible_info::dangerous, mtype::difficulty, avatar::get_mon_visible(), catacurses::getmaxx(), catacurses::getmaxy(), mvwprintz(), om_direction::name(), mtype::nname(), NPCATT_FOLLOW, NPCATT_KILL, pgettext(), string_format(), mtype::sym, type, u, monster_visible_info::unique_mons, monster_visible_info::unique_types, utf8_width(), point::x, and point::y.

◆ mon_info_update()

void game::mon_info_update ( )

Definition at line 3843 of file game.cpp.

3844{
3845 int newseen = 0;
3846 const int safe_proxy_dist = get_option<int>( "SAFEMODEPROXIMITY" );
3847 const int iProxyDist = ( safe_proxy_dist <= 0 ) ? MAX_VIEW_DISTANCE :
3848 safe_proxy_dist;
3849
3850 monster_visible_info &mon_visible = u.get_mon_visible();
3851 auto &new_seen_mon = mon_visible.new_seen_mon;
3852 auto &unique_types = mon_visible.unique_types;
3853 auto &unique_mons = mon_visible.unique_mons;
3854 auto &dangerous = mon_visible.dangerous;
3855
3856 // 7 0 1 unique_types uses these indices;
3857 // 6 8 2 0-7 are provide by direction_from()
3858 // 5 4 3 8 is used for local monsters (for when we explain them below)
3859 for( auto &t : unique_types ) {
3860 t.clear();
3861 }
3862 for( auto &m : unique_mons ) {
3863 m.clear();
3864 }
3865 std::fill( dangerous, dangerous + 8, false );
3866
3867 const tripoint view = u.pos() + u.view_offset;
3868 new_seen_mon.clear();
3869
3870 // TODO: no reason to have it static here
3871 static time_point previous_turn = calendar::start_of_cataclysm;
3872 const time_duration sm_ignored_time = time_duration::from_turns(
3873 get_option<int>( "SAFEMODEIGNORETURNS" ) );
3874
3876 monster *m = dynamic_cast<monster *>( c );
3877 npc *p = dynamic_cast<npc *>( c );
3878 const direction dir_to_mon = direction_from( view.xy(), point( c->posx(), c->posy() ) );
3879 const int mx = POSX + ( c->posx() - view.x );
3880 const int my = POSY + ( c->posy() - view.y );
3881 int index = 8;
3882 if( !is_valid_in_w_terrain( point( mx, my ) ) ) {
3883 // for compatibility with old code, see diagram below, it explains the values for index,
3884 // also might need revisiting one z-levels are in.
3885 switch( dir_to_mon ) {
3889 index = 7;
3890 break;
3892 case direction::NORTH:
3894 index = 0;
3895 break;
3899 index = 1;
3900 break;
3902 case direction::WEST:
3904 index = 6;
3905 break;
3907 case direction::CENTER:
3909 index = 8;
3910 break;
3912 case direction::EAST:
3914 index = 2;
3915 break;
3919 index = 5;
3920 break;
3922 case direction::SOUTH:
3924 index = 4;
3925 break;
3929 index = 3;
3930 break;
3931 }
3932 }
3933
3934 rule_state safemode_state = RULE_NONE;
3935 const bool safemode_empty = get_safemode().empty();
3936
3937 if( m != nullptr ) {
3938 //Safemode monster check
3939 monster &critter = *m;
3940
3941 const monster_attitude matt = critter.attitude( &u );
3942 const int mon_dist = rl_dist( u.pos(), critter.pos() );
3943 safemode_state = get_safemode().check_monster( critter.name(), critter.attitude_to( u ), mon_dist );
3944
3945 if( ( !safemode_empty && safemode_state == RULE_BLACKLISTED ) || ( safemode_empty &&
3946 ( MATT_ATTACK == matt || MATT_FOLLOW == matt ) ) ) {
3947 if( index < 8 && critter.sees( g->u ) ) {
3948 dangerous[index] = true;
3949 }
3950
3951 if( !safemode_empty || mon_dist <= iProxyDist ) {
3952 bool passmon = false;
3953 if( critter.ignoring > 0 ) {
3954 if( safe_mode != SAFE_MODE_ON ) {
3955 critter.ignoring = 0;
3956 } else if( ( sm_ignored_time == 0_seconds || ( critter.lastseen_turn &&
3957 *critter.lastseen_turn > calendar::turn - sm_ignored_time ) ) &&
3958 ( mon_dist > critter.ignoring / 2 || mon_dist < 6 ) ) {
3959 passmon = true;
3960 }
3961 critter.lastseen_turn = calendar::turn;
3962 }
3963
3964 if( !passmon ) {
3965 newseen++;
3966 new_seen_mon.push_back( shared_from( critter ) );
3967 }
3968 }
3969 }
3970
3971 std::vector<std::pair<const mtype *, int>> &vec = unique_mons[index];
3972 const auto mon_it = std::find_if( vec.begin(), vec.end(),
3973 [&]( const std::pair<const mtype *, int> &elem ) {
3974 return elem.first == critter.type;
3975 } );
3976 if( mon_it == vec.end() ) {
3977 vec.emplace_back( critter.type, 1 );
3978 } else {
3979 mon_it->second++;
3980 }
3981 } else if( p != nullptr ) {
3982 //Safe mode NPC check
3983
3984 const int npc_dist = rl_dist( u.pos(), p->pos() );
3985 safemode_state = get_safemode().check_monster( get_safemode().npc_type_name(), p->attitude_to( u ),
3986 npc_dist );
3987
3988 if( ( !safemode_empty && safemode_state == RULE_BLACKLISTED ) || ( safemode_empty &&
3989 p->get_attitude() == NPCATT_KILL ) ) {
3990 if( !safemode_empty || npc_dist <= iProxyDist ) {
3991 newseen++;
3992 }
3993 }
3994 unique_types[index].push_back( p );
3995 }
3996 }
3997
3998 if( newseen > mostseen ) {
3999 if( newseen - mostseen == 1 ) {
4000 if( !new_seen_mon.empty() ) {
4001 monster &critter = *new_seen_mon.back();
4003 string_format( _( "%s spotted!" ), critter.name() ) );
4004 if( u.has_trait( trait_id( "M_DEFENDER" ) ) && critter.type->in_species( PLANT ) ) {
4005 add_msg( m_warning, _( "We have detected a %s - an enemy of the Mycus!" ), critter.name() );
4007 u.add_effect( effect_adrenaline_mycus, 30_minutes );
4008 } else if( u.get_effect_int( effect_adrenaline_mycus ) == 1 ) {
4009 // Triffids present. We ain't got TIME to adrenaline comedown!
4010 u.add_effect( effect_adrenaline_mycus, 15_minutes );
4011 u.mod_pain( 3 ); // Does take it out of you, though
4012 add_msg( m_info, _( "Our fibers strain with renewed wrath!" ) );
4013 }
4014 }
4015 } else {
4016 //Hostile NPC
4018 _( "Hostile survivor spotted!" ) );
4019 }
4020 } else {
4022 }
4024 if( safe_mode == SAFE_MODE_ON ) {
4026 }
4027 } else if( calendar::turn > previous_turn && get_option<bool>( "AUTOSAFEMODE" ) &&
4028 newseen == 0 ) { // Auto-safe mode, but only if it's a new turn
4029 turnssincelastmon += to_turns<int>( calendar::turn - previous_turn );
4030 if( turnssincelastmon >= get_option<int>( "AUTOSAFEMODETURNS" ) && safe_mode == SAFE_MODE_OFF ) {
4032 add_msg( m_info, _( "Safe mode ON!" ) );
4033 }
4034 }
4035
4036 if( newseen == 0 && safe_mode == SAFE_MODE_STOP ) {
4038 }
4039
4040 previous_turn = calendar::turn;
4041 mostseen = newseen;
4042}
int get_effect_int(const efftype_id &eff_id, body_part bp=num_bp) const
Returns the intensity of the matching effect.
Definition: creature.cpp:1291
virtual bool sees(const Creature &critter) const
The functions check whether this creature can see the target.
Definition: creature.cpp:205
bool cancel_activity_or_ignore_query(distraction_type type, const std::string &text)
Asks if the player wants to cancel their activity and if so cancels it.
Definition: game.cpp:1701
monster_attitude attitude(const Character *u=nullptr) const
Definition: monster.cpp:1098
std::optional< time_point > lastseen_turn
Definition: monster.h:506
Attitude attitude_to(const Creature &other) const override
Attitude (of this creature) towards another creature.
Definition: npc.cpp:2082
rule_state check_monster(const std::string &creature_name_in, Creature::Attitude attitude_in, int proximity_in) const
bool empty() const
rule_state
Definition: enums.h:51
@ RULE_NONE
Definition: enums.h:52
static const species_id PLANT("PLANT")
static const efftype_id effect_adrenaline_mycus("adrenaline_mycus")
bool is_valid_in_w_terrain(point p)
Definition: game.cpp:290
static constexpr int MAPSIZE_X
monster_attitude
Definition: monster.h:55
@ MATT_FOLLOW
Definition: monster.h:61
@ MATT_ATTACK
Definition: monster.h:62
FMT_NOINLINE OutputIt fill(OutputIt it, size_t n, const fill_t< Char > &fill)
bool in_species(const species_id &spec) const
Definition: mtype.cpp:122

References _, ABOVECENTER, ABOVEEAST, ABOVENORTH, ABOVENORTHEAST, ABOVENORTHWEST, ABOVESOUTH, ABOVESOUTHEAST, ABOVESOUTHWEST, ABOVEWEST, Creature::add_effect(), add_msg(), monster::attitude(), monster::attitude_to(), npc::attitude_to(), BELOWCENTER, BELOWEAST, BELOWNORTH, BELOWNORTHEAST, BELOWNORTHWEST, BELOWSOUTH, BELOWSOUTHEAST, BELOWSOUTHWEST, BELOWWEST, c, cancel_activity_or_ignore_query(), CENTER, safemode::check_monster(), monster_visible_info::dangerous, direction_from(), EAST, effect_adrenaline_mycus, safemode::empty(), detail::fill(), time_duration::from_turns(), g, npc::get_attitude(), Creature::get_effect_int(), avatar::get_mon_visible(), get_safemode(), Character::get_visible_creatures(), Creature::has_effect(), Character::has_trait(), hostile_spotted_far, monster::ignoring, mtype::in_species(), is_valid_in_w_terrain(), monster::lastseen_turn, m, m_info, m_warning, MAPSIZE_X, MATT_ATTACK, MATT_FOLLOW, MAX_VIEW_DISTANCE, Character::mod_pain(), mostseen, monster::name(), monster_visible_info::new_seen_mon, NORTH, NORTHEAST, NORTHWEST, NPCATT_KILL, PLANT, Character::pos(), monster::pos(), POSX, POSY, rl_dist(), RULE_BLACKLISTED, RULE_NONE, safe_mode, SAFE_MODE_OFF, SAFE_MODE_ON, SAFE_MODE_STOP, Creature::sees(), set_safe_mode(), shared_from(), SOUTH, SOUTHEAST, SOUTHWEST, calendar::start_of_cataclysm, string_format(), calendar::turn, turnssincelastmon, monster::type, u, monster_visible_info::unique_mons, monster_visible_info::unique_types, player::view_offset, WEST, tripoint::x, tripoint::xy(), and tripoint::y.

Referenced by do_turn().

◆ monmove()

void game::monmove ( )
private

Definition at line 4079 of file game.cpp.

4080{
4081 cleanup_dead();
4082
4083 for( monster &critter : all_monsters() ) {
4084 // Critters in impassable tiles get pushed away, unless it's not impassable for them
4085 if( !critter.is_dead() && m.impassable( critter.pos() ) && !critter.can_move_to( critter.pos() ) ) {
4086 std::string msg = string_format( "%s can't move to its location! %s %s", critter.name(),
4087 critter.pos().to_string(), m.tername( critter.pos() ) );
4088 dbg( DL::Error ) << msg;
4089 add_msg( m_debug, msg );
4090 bool okay = false;
4091 for( const tripoint &dest : m.points_in_radius( critter.pos(), 3 ) ) {
4092 if( critter.can_move_to( dest ) && is_empty( dest ) ) {
4093 critter.setpos( dest );
4094 okay = true;
4095 break;
4096 }
4097 }
4098 if( !okay ) {
4099 // die of "natural" cause (overpopulation is natural)
4100 critter.die( nullptr );
4101 }
4102 }
4103
4104 if( !critter.is_dead() ) {
4105 critter.process_items();
4106 }
4107
4108 if( !critter.is_dead() ) {
4109 critter.process_turn();
4110 }
4111
4112 m.creature_in_field( critter );
4113 if( calendar::once_every( 1_days ) ) {
4114 if( critter.has_flag( MF_MILKABLE ) ) {
4115 critter.refill_udders();
4116 }
4117 critter.try_reproduce();
4118 }
4119 while( critter.moves > 0 && !critter.is_dead() && !critter.has_effect( effect_ridden ) ) {
4120 critter.made_footstep = false;
4121 // Controlled critters don't make their own plans
4122 if( !critter.has_effect( effect_ai_controlled ) ) {
4123 // Formulate a path to follow
4124 critter.plan();
4125 }
4126 critter.move(); // Move one square, possibly hit u
4127 critter.process_triggers();
4128 m.creature_in_field( critter );
4129 }
4130
4131 const bionic_id bio_alarm( "bio_alarm" );
4132 if( !critter.is_dead() &&
4133 u.has_active_bionic( bio_alarm ) &&
4134 u.get_power_level() >= bio_alarm->power_trigger &&
4135 rl_dist( u.pos(), critter.pos() ) <= 5 &&
4136 !critter.is_hallucination() ) {
4137 u.mod_power_level( -bio_alarm->power_trigger );
4138 add_msg( m_warning, _( "Your motion alarm goes off!" ) );
4140 _( "Your motion alarm goes off!" ) );
4141 if( u.has_effect( efftype_id( "sleep" ) ) ) {
4142 u.wake_up();
4143 }
4144 }
4145 }
4146
4147 cleanup_dead();
4148
4149 // The remaining monsters are all alive, but may be outside of the reality bubble.
4150 // If so, despawn them. This is not the same as dying, they will be stored for later and the
4151 // monster::die function is not called.
4152 for( monster &critter : all_monsters() ) {
4153 if( critter.posx() < 0 - ( MAPSIZE_X ) / 6 ||
4154 critter.posy() < 0 - ( MAPSIZE_Y ) / 6 ||
4155 critter.posx() > ( MAPSIZE_X * 7 ) / 6 ||
4156 critter.posy() > ( MAPSIZE_Y * 7 ) / 6 ) {
4157 despawn_monster( critter );
4158 }
4159 }
4160
4161 // Now, do active NPCs.
4162 for( npc &guy : g->all_npcs() ) {
4163 int turns = 0;
4164 if( guy.is_mounted() ) {
4165 guy.check_mount_is_spooked();
4166 }
4167 m.creature_in_field( guy );
4168 if( !guy.has_effect( effect_npc_suspend ) ) {
4169 guy.process_turn();
4170 }
4171 while( !guy.is_dead() && guy.moves > 0 && turns < 10 &&
4172 ( !guy.in_sleep_state() || guy.activity.id() == ACT_OPERATION )
4173 ) {
4174 int moves = guy.moves;
4175 guy.move();
4176 if( moves == guy.moves ) {
4177 // Count every time we exit npc::move() without spending any moves.
4178 turns++;
4179 }
4180
4181 // Turn on debug mode when in infinite loop
4182 // It has to be done before the last turn, otherwise
4183 // there will be no meaningful debug output.
4184 if( turns == 9 ) {
4185 debugmsg( "NPC %s entered infinite loop. Turning on debug mode",
4186 guy.name );
4187 debug_mode = true;
4188 }
4189 }
4190
4191 // If we spun too long trying to decide what to do (without spending moves),
4192 // Invoke cognitive suspension to prevent an infinite loop.
4193 if( turns == 10 ) {
4194 add_msg( _( "%s faints!" ), guy.name );
4195 guy.reboot();
4196 }
4197
4198 if( !guy.is_dead() ) {
4199 guy.npc_update_body();
4200 }
4201 }
4202 cleanup_dead();
4203}
void mod_power_level(const units::energy &npower)
Definition: character.cpp:1925
units::energy get_power_level() const
Definition: character.cpp:1905
void wake_up()
Definition: avatar.cpp:959
static const activity_id ACT_OPERATION("ACT_OPERATION")
static const efftype_id effect_npc_suspend("npc_suspend")
static const efftype_id effect_ai_controlled("ai_controlled")
static constexpr int MAPSIZE_Y
@ MF_MILKABLE
Definition: mtype.h:167

References _, ACT_OPERATION, add_msg(), alert, all_monsters(), cancel_activity_or_ignore_query(), cleanup_dead(), map::creature_in_field(), dbg, debug_mode, debugmsg, despawn_monster(), anonymous_namespace{iexamine_elevator.cpp}::elevator::dest(), effect_ai_controlled, effect_npc_suspend, effect_ridden, Error, g, Character::get_power_level(), Character::has_active_bionic(), Creature::has_effect(), map::impassable(), is_empty(), m, m_debug, m_warning, MAPSIZE_X, MAPSIZE_Y, MF_MILKABLE, Character::mod_power_level(), calendar::once_every(), map::points_in_radius(), Character::pos(), bionic_data::power_trigger, rl_dist(), string_format(), map::tername(), u, and avatar::wake_up().

Referenced by do_turn().

◆ mouse_edge_scrolling()

std::pair< tripoint, tripoint > game::mouse_edge_scrolling ( input_context ctxt,
int  speed,
const tripoint last,
bool  iso 
)
private

Definition at line 2027 of file game.cpp.

2029{
2030 const int rate = get_option<int>( "EDGE_SCROLL" );
2031 auto ret = std::make_pair( tripoint_zero, last );
2032 if( rate == -1 ) {
2033 // Fast return when the option is disabled.
2034 return ret;
2035 }
2036 // Ensure the parameters are used even if the #if below is false
2037 ( void ) ctxt;
2038 ( void ) speed;
2039 ( void ) iso;
2040#if (defined TILES || defined _WIN32 || defined WINDOWS)
2041 auto now = std::chrono::steady_clock::now();
2042 if( now < last_mouse_edge_scroll + std::chrono::milliseconds( rate ) ) {
2043 return ret;
2044 } else {
2046 }
2047 const input_event event = ctxt.get_raw_input();
2048 if( event.type == CATA_INPUT_MOUSE ) {
2049 const point threshold( projected_window_width() / 100, projected_window_height() / 100 );
2050 if( event.mouse_pos.x <= threshold.x ) {
2051 ret.first.x -= speed;
2052 if( iso ) {
2053 ret.first.y -= speed;
2054 }
2055 } else if( event.mouse_pos.x >= projected_window_width() - threshold.x ) {
2056 ret.first.x += speed;
2057 if( iso ) {
2058 ret.first.y += speed;
2059 }
2060 }
2061 if( event.mouse_pos.y <= threshold.y ) {
2062 ret.first.y -= speed;
2063 if( iso ) {
2064 ret.first.x += speed;
2065 }
2066 } else if( event.mouse_pos.y >= projected_window_height() - threshold.y ) {
2067 ret.first.y += speed;
2068 if( iso ) {
2069 ret.first.x -= speed;
2070 }
2071 }
2072 ret.second = ret.first;
2073 } else if( event.type == CATA_INPUT_TIMEOUT ) {
2074 ret.first = ret.second;
2075 }
2076#endif
2077 return ret;
2078}
@ CATA_INPUT_TIMEOUT
Definition: input.h:77
@ CATA_INPUT_MOUSE
Definition: input.h:80

References CATA_INPUT_MOUSE, CATA_INPUT_TIMEOUT, input_context::get_raw_input(), iso, last, last_mouse_edge_scroll, cata::hash64_detail::ret, tripoint_zero, point::x, and point::y.

Referenced by mouse_edge_scrolling_overmap(), and mouse_edge_scrolling_terrain().

◆ mouse_edge_scrolling_overmap()

tripoint game::mouse_edge_scrolling_overmap ( input_context ctxt)

This variant is suitable for the overmap.

Definition at line 2089 of file game.cpp.

2090{
2091 // overmap has no iso mode
2095 return ret.first;
2096}
std::pair< tripoint, tripoint > mouse_edge_scrolling(input_context &ctxt, int speed, const tripoint &last, bool iso)
Definition: game.cpp:2027
tripoint last_mouse_edge_scroll_vector_terrain
Definition: game.h:1068
tripoint last_mouse_edge_scroll_vector_overmap
Definition: game.h:1069

References last_mouse_edge_scroll_vector_overmap, last_mouse_edge_scroll_vector_terrain, mouse_edge_scrolling(), cata::hash64_detail::ret, and tripoint_zero.

◆ mouse_edge_scrolling_terrain()

tripoint game::mouse_edge_scrolling_terrain ( input_context ctxt)

Used to implement mouse "edge scrolling".

Returns a tripoint which is a vector of the resulting "move", i.e. (0, 0, 0) if the mouse is not at the edge of the screen, otherwise some (x, y, 0) depending on which edges are hit. This variant adjust scrolling speed according to zoom level, making it suitable when viewing the "terrain".

Definition at line 2080 of file game.cpp.

References DEFAULT_TILESET_ZOOM, last_mouse_edge_scroll_vector_overmap, last_mouse_edge_scroll_vector_terrain, mouse_edge_scrolling(), cata::hash64_detail::ret, tile_iso, tileset_zoom, and tripoint_zero.

Referenced by look_around().

◆ move_save_to_graveyard()

void game::move_save_to_graveyard ( const std::string &  dirname)
private

Definition at line 2472 of file game.cpp.

2473{
2474 const std::string save_dir = get_world_base_save_path();
2475 const std::string graveyard_dir = PATH_INFO::graveyarddir() + "/";
2476 const std::string graveyard_save_dir = graveyard_dir + dirname + "/";
2477 const std::string &prefix = base64_encode( u.get_save_id() ) + ".";
2478
2479 if( !assure_dir_exist( graveyard_dir ) ) {
2480 debugmsg( "could not create graveyard path '%s'", graveyard_dir );
2481 }
2482
2483 if( !assure_dir_exist( graveyard_save_dir ) ) {
2484 debugmsg( "could not create graveyard path '%s'", graveyard_save_dir );
2485 }
2486
2487 const auto save_files = get_files_from_path( prefix, save_dir );
2488 if( save_files.empty() ) {
2489 debugmsg( "could not find save files in '%s'", save_dir );
2490 }
2491
2492 for( const auto &src_path : save_files ) {
2493 const std::string dst_path = graveyard_save_dir +
2494 src_path.substr( src_path.rfind( '/' ), std::string::npos );
2495
2496 if( rename_file( src_path, dst_path ) ) {
2497 continue;
2498 }
2499
2500 debugmsg( "could not rename file '%s' to '%s'", src_path, dst_path );
2501
2502 if( remove_file( src_path ) ) {
2503 continue;
2504 }
2505
2506 debugmsg( "could not remove file '%s'", src_path );
2507 }
2508}
bool remove_file(const std::string &path)
Remove a file.
Definition: filesystem.cpp:89
bool assure_dir_exist(const std::string &path)
Create directory if it does not exist.
Definition: filesystem.cpp:48
bool rename_file(const std::string &old_path, const std::string &new_path)
Rename a file, overwriting the target.
Definition: filesystem.cpp:105
std::vector< std::string > get_files_from_path(const std::string &pattern, const std::string &root_path, const bool recursive_search, const bool match_extension)
Returns a vector of files or directories matching pattern at root_path.
Definition: filesystem.cpp:366
std::string graveyarddir()
Definition: path_info.cpp:202

References assure_dir_exist(), base64_encode(), debugmsg, get_files_from_path(), avatar::get_save_id(), get_world_base_save_path(), PATH_INFO::graveyarddir(), prefix, remove_file(), rename_file(), and u.

Referenced by cleanup_at_end().

◆ moving_vehicle_dismount()

void game::moving_vehicle_dismount ( const tripoint dest_loc)

Handles players exiting from moving vehicles.

Definition at line 5153 of file game.cpp.

5154{
5155 const optional_vpart_position vp = m.veh_at( u.pos() );
5156 if( !vp ) {
5157 debugmsg( "Tried to exit non-existent vehicle." );
5158 return;
5159 }
5160 vehicle *const veh = &vp->vehicle();
5161 if( u.pos() == dest_loc ) {
5162 debugmsg( "Need somewhere to dismount towards." );
5163 return;
5164 }
5165 tileray ray( dest_loc.xy() + point( -u.posx(), -u.posy() ) );
5166 // TODO:: make dir() const correct!
5167 const units::angle d = ray.dir();
5168 add_msg( _( "You dive from the %s." ), veh->name );
5169 m.unboard_vehicle( u.pos() );
5170 u.moves -= 200;
5171 // Dive three tiles in the direction of tox and toy
5172 fling_creature( &u, d, 30, true );
5173 // Hit the ground according to vehicle speed
5174 if( !m.has_flag( "SWIMMABLE", u.pos() ) ) {
5175 if( veh->velocity > 0 ) {
5176 fling_creature( &u, veh->face.dir(), veh->velocity / static_cast<float>( 100 ) );
5177 } else {
5178 fling_creature( &u, veh->face.dir() + 180_degrees,
5179 -( veh->velocity ) / static_cast<float>( 100 ) );
5180 }
5181 }
5182}
void fling_creature(Creature *c, const units::angle &dir, float flvel, bool controlled=false)
Flings the input creature in the given direction.
Definition: game.cpp:9800

References _, add_msg(), debugmsg, tileray::dir(), vehicle::face, fling_creature(), map::has_flag(), m, Creature::moves, vehicle::name, Character::pos(), Character::posx(), Character::posy(), u, map::unboard_vehicle(), map::veh_at(), vehicle::velocity, and tripoint::xy().

◆ natural_light_level()

float game::natural_light_level ( int  zlev) const

Definition at line 3508 of file game.cpp.

3509{
3510 // ignore while underground or above limits
3511 if( zlev > OVERMAP_HEIGHT || zlev < 0 ) {
3512 return LIGHT_AMBIENT_MINIMAL;
3513 }
3514
3515 if( latest_lightlevels[zlev] > -std::numeric_limits<float>::max() ) {
3516 // Already found the light level for now?
3517 return latest_lightlevels[zlev];
3518 }
3519
3520 float ret = LIGHT_AMBIENT_MINIMAL;
3521
3522 // Sunlight/moonlight related stuff
3524 if( !weather.lightning_active ) {
3526 } else {
3527 // Recent lightning strike has lit the area
3529 }
3530
3532
3533 // Artifact light level changes here. Even though some of these only have an effect
3534 // aboveground it is cheaper performance wise to simply iterate through the entire
3535 // list once instead of twice.
3536 float mod_ret = -1;
3537 // Each artifact change does std::max(mod_ret, new val) since a brighter end value
3538 // will trump a lower one.
3539 if( const timed_event *e = timed_events.get( TIMED_EVENT_DIM ) ) {
3540 // TIMED_EVENT_DIM slowly dims the natural sky level, then relights it.
3541 const time_duration left = e->when - calendar::turn;
3542 // TIMED_EVENT_DIM has an occurrence date of turn + 50, so the first 25 dim it,
3543 if( left > 25_turns ) {
3544 mod_ret = std::max( static_cast<double>( mod_ret ), ( ret * ( left - 25_turns ) ) / 25_turns );
3545 // and the last 25 scale back towards normal.
3546 } else {
3547 mod_ret = std::max( static_cast<double>( mod_ret ), ( ret * ( 25_turns - left ) ) / 25_turns );
3548 }
3549 }
3551 // TIMED_EVENT_ARTIFACT_LIGHT causes everywhere to become as bright as day.
3552 mod_ret = std::max<float>( ret, default_daylight_level() );
3553 }
3554 // If we had a changed light level due to an artifact event then it overwrites
3555 // the natural light level.
3556 if( mod_ret > -1 ) {
3557 ret = mod_ret;
3558 }
3559
3560 // Cap everything to our minimum light level
3561 ret = std::max<float>( LIGHT_AMBIENT_MINIMAL, ret );
3562
3563 latest_lightlevels[zlev] = ret;
3564
3565 return ret;
3566}
double default_daylight_level()
How much light is provided in full daylight.
Definition: calendar.cpp:62
float sunlight(const time_point &p, const bool vision)
Returns the current sunlight or moonlight level through the preceding functions.
Definition: calendar.cpp:199
std::array< float, OVERMAP_LAYERS > latest_lightlevels
Definition: game.h:1041
bool queued(timed_event_type type) const
timed_event * get(timed_event_type type)
weather_type_id weather_id
Definition: weather.h:193
static constexpr float LIGHT_AMBIENT_MINIMAL
Definition: lightmap.h:12
@ TIMED_EVENT_DIM
Definition: timed_event.h:22
@ TIMED_EVENT_ARTIFACT_LIGHT
Definition: timed_event.h:23

References default_daylight_level(), timed_event_manager::get(), get_weather, latest_lightlevels, left, LIGHT_AMBIENT_MINIMAL, weather_type::light_modifier, OVERMAP_HEIGHT, timed_event_manager::queued(), cata::hash64_detail::ret, sunlight(), TIMED_EVENT_ARTIFACT_LIGHT, TIMED_EVENT_DIM, timed_events, calendar::turn, and weather_manager::weather_id.

Referenced by light_level().

◆ npc_menu()

bool game::npc_menu ( npc who)

Returns true if the menu handled stuff and player shouldn't do anything else.

Perception slightly increases precision when examining NPCs' wounds Firstaid increases precision when examining NPCs' wounds

Definition at line 5284 of file game.cpp.

5285{
5286 enum choices : int {
5287 talk = 0,
5288 swap_pos,
5289 push,
5290 examine_wounds,
5291 use_item,
5292 sort_armor,
5293 attack,
5294 disarm,
5295 steal
5296 };
5297
5298 const bool obeys = debug_mode || ( who.is_player_ally() && !who.in_sleep_state() );
5299
5300 uilist amenu;
5301
5302 amenu.text = string_format( _( "What to do with %s?" ), who.disp_name() );
5303 amenu.addentry( talk, true, 't', _( "Talk" ) );
5304 amenu.addentry( swap_pos, obeys && !who.is_mounted() &&
5305 !u.is_mounted(), 's', _( "Swap positions" ) );
5306 amenu.addentry( push, obeys && !who.is_mounted(), 'p', _( "Push away" ) );
5307 amenu.addentry( examine_wounds, true, 'w', _( "Examine wounds" ) );
5308 amenu.addentry( use_item, true, 'i', _( "Use item on" ) );
5309 amenu.addentry( sort_armor, obeys, 'r', _( "Sort armor" ) );
5310 amenu.addentry( attack, true, 'a', _( "Attack" ) );
5311 if( !who.is_player_ally() ) {
5312 amenu.addentry( disarm, who.is_armed(), 'd', _( "Disarm" ) );
5313 amenu.addentry( steal, !who.is_enemy(), 'S', _( "Steal" ) );
5314 }
5315
5316 amenu.query();
5317
5318 const int choice = amenu.ret;
5319 if( choice == talk ) {
5320 who.talk_to_u();
5321 } else if( choice == swap_pos ) {
5322 if( !prompt_dangerous_tile( who.pos() ) ) {
5323 return true;
5324 }
5325 // TODO: Make NPCs protest when displaced onto dangerous crap
5326 add_msg( _( "You swap places with %s." ), who.name );
5327 swap_critters( u, who );
5328 // TODO: Make that depend on stuff
5329 u.mod_moves( -200 );
5330 } else if( choice == push ) {
5331 // TODO: Make NPCs protest when displaced onto dangerous crap
5332 tripoint oldpos = who.pos();
5333 who.move_away_from( u.pos(), true );
5334 u.mod_moves( -20 );
5335 if( oldpos != who.pos() ) {
5336 add_msg( _( "%s moves out of the way." ), who.name );
5337 } else {
5338 add_msg( m_warning, _( "%s has nowhere to go!" ), who.name );
5339 }
5340 } else if( choice == examine_wounds ) {
5341 ///\EFFECT_PER slightly increases precision when examining NPCs' wounds
5342
5343 ///\EFFECT_FIRSTAID increases precision when examining NPCs' wounds
5344 const bool precise = u.get_skill_level( skill_firstaid ) * 4 + u.per_cur >= 20;
5345 who.body_window( _( "Limbs of: " ) + who.disp_name(), true, precise, 0, 0, 0, 0.0f, 0.0f, 0.0f,
5346 0.0f, 0.0f );
5347 } else if( choice == use_item ) {
5348 static const std::string heal_string( "heal" );
5349 const auto will_accept = []( const item & it ) {
5350 const auto use_fun = it.get_use( heal_string );
5351 if( use_fun == nullptr ) {
5352 return false;
5353 }
5354
5355 const auto *actor = dynamic_cast<const heal_actor *>( use_fun->get_actor_ptr() );
5356
5357 return actor != nullptr &&
5358 actor->limb_power >= 0 &&
5359 actor->head_power >= 0 &&
5360 actor->torso_power >= 0;
5361 };
5362 item_location loc = game_menus::inv::titled_filter_menu( will_accept, u, _( "Use which item?" ) );
5363
5364 if( !loc ) {
5365 add_msg( _( "Never mind" ) );
5366 return false;
5367 }
5368 item &used = *loc;
5369 bool did_use = u.invoke_item( &used, heal_string, who.pos() );
5370 if( did_use ) {
5371 // Note: exiting a body part selection menu counts as use here
5372 u.mod_moves( -300 );
5373 }
5374 } else if( choice == sort_armor ) {
5375 show_armor_layers_ui( who );
5376 u.mod_moves( -100 );
5377 } else if( choice == attack ) {
5378 if( who.is_enemy() || query_yn( _( "You may be attacked! Proceed?" ) ) ) {
5379 u.melee_attack( who, true );
5380 who.on_attacked( u );
5381 }
5382 } else if( choice == disarm ) {
5383 if( who.is_enemy() || query_yn( _( "You may be attacked! Proceed?" ) ) ) {
5385 }
5386 } else if( choice == steal && query_yn( _( "You may be attacked! Proceed?" ) ) ) {
5388 }
5389
5390 return true;
5391}
hp_part body_window(const std::string &menu_header, bool show_all, bool precise, int normal_bonus, int head_bonus, int torso_bonus, float bleed, float bite, float infect, float bandage_power, float disinfectant_power) const
Displays menu with body part hp, optionally with hp estimation after healing.
Definition: character.cpp:5750
bool in_sleep_state() const override
Definition: character.cpp:9323
void melee_attack(Creature &t, bool allow_special, const matec_id *force_technique=nullptr, bool allow_unarmed=true)
Sets up a melee attack and handles melee attack function calls.
Definition: melee.cpp:445
int per_cur
Definition: character.h:267
bool prompt_dangerous_tile(const tripoint &dest_loc) const
Definition: game.cpp:8725
bool swap_critters(Creature &, Creature &)
Swaps positions of two creatures.
Definition: game.cpp:4779
float limb_power
How much hp to restore when healing limbs?
Definition: iuse_actor.h:1012
void talk_to_u(bool radio_contact=false)
Definition: npctalk.cpp:769
void on_attacked(const Creature &attacker)
Definition: npc.cpp:1446
void move_away_from(const tripoint &p, bool no_bash_atk=false, std::set< tripoint > *nomove=nullptr)
Definition: npcmove.cpp:2575
static const skill_id skill_firstaid("firstaid")
static void swap_pos(Creature &caster, const tripoint &target)
void try_disarm_npc(avatar &you, npc &target)
Try to disarm the NPC.
Definition: melee.cpp:2379
void try_steal_from_npc(avatar &you, npc &target)
Try to steal an item from the NPC's inventory.
Definition: melee.cpp:2456
item_location steal(avatar &you, player &victim)
Menu for stealing stuff.
item_location titled_filter_menu(item_filter filter, avatar &you, const std::string &title, const std::string &none_message="")
void push(monster &z)
Definition: monexamine.cpp:615

References _, add_msg(), uilist::addentry(), Character::body_window(), debug_mode, Character::disp_name(), Character::get_skill_level(), Character::in_sleep_state(), avatar::invoke_item(), Character::is_armed(), npc::is_enemy(), Character::is_mounted(), npc::is_player_ally(), heal_actor::limb_power, m_warning, Character::melee_attack(), Creature::mod_moves(), npc::move_away_from(), Character::name, npc::on_attacked(), Character::per_cur, Character::pos(), prompt_dangerous_tile(), monexamine::push(), uilist::query(), query_yn(), uilist::ret, show_armor_layers_ui(), skill_firstaid, game_menus::inv::steal(), string_format(), swap_critters(), swap_pos(), npc::talk_to_u(), uilist::text, game_menus::inv::titled_filter_menu(), avatar_funcs::try_disarm_npc(), avatar_funcs::try_steal_from_npc(), u, and avatar_action::use_item().

Referenced by examine().

◆ num_creatures()

size_t game::num_creatures ( ) const

Returns the approximate number of creatures in the reality bubble.

Because of performance restrictions it may return a slightly incorrect values (as it includes dead, but not yet cleaned up creatures).

Definition at line 4725 of file game.cpp.

4726{
4727 return critter_tracker->size() + active_npc.size() + 1; // 1 == g->u
4728}

References active_npc, and critter_tracker.

Referenced by display_visibility(), and fungal_effects::fungalize().

◆ on_move_effects()

void game::on_move_effects ( )

Definition at line 9758 of file game.cpp.

9759{
9760 // TODO: Move this to a character method
9761 if( !u.is_mounted() ) {
9762 const item muscle( "muscle" );
9763 for( const bionic_id &bid : u.get_bionic_fueled_with( muscle ) ) {
9764 if( u.has_active_bionic( bid ) ) {// active power gen
9765 u.mod_power_level( units::from_kilojoule( muscle.fuel_energy() ) * bid->fuel_efficiency );
9766 } else if( u.has_bionic( bid ) ) {// passive power gen
9767 u.mod_power_level( units::from_kilojoule( muscle.fuel_energy() ) * bid->passive_fuel_efficiency );
9768 }
9769 }
9770 const bionic_id bio_jointservo( "bio_jointservo" );
9772 if( u.movement_mode_is( CMM_RUN ) ) {
9774 } else {
9776 }
9777 }
9778 }
9779
9780 if( u.movement_mode_is( CMM_RUN ) ) {
9781 if( !u.can_run() ) {
9783 }
9784 }
9785
9786 // apply martial art move bonuses
9787 u.martial_arts_data->ma_onmove_effects( u );
9788
9790}
static const bionic_id bio_jointservo("bio_jointservo")
@ CMM_RUN
Definition: character.h:110
bool can_run()
source of truth of whether a Character can run
Definition: character.cpp:1270
bool movement_mode_is(character_movemode mode) const
Check against the character's current movement mode.
Definition: character.cpp:1560
std::vector< bionic_id > get_bionic_fueled_with(const item &it) const
Return bionic_id of bionics able to use it as fuel.
Definition: character.cpp:1866
bool has_bionic(const bionic_id &b) const
Returns true if the player has the entered bionic id.
Definition: character.cpp:1815
void do_ambient()
Definition: sounds.cpp:1615
constexpr quantity< value_type, energy_in_joule_tag > from_kilojoule(const value_type v)
Definition: units_energy.h:32
units::energy power_trigger
Power cost when the bionic's special effect is triggered.
Definition: bionics.h:43

References bio_jointservo, Character::can_run(), CMM_RUN, sfx::do_ambient(), units::from_kilojoule(), item::fuel_energy(), Character::get_bionic_fueled_with(), Character::has_active_bionic(), Character::has_bionic(), Character::is_mounted(), Character::martial_arts_data, Character::mod_power_level(), Character::movement_mode_is(), bionic_data::power_trigger, avatar::toggle_run_mode(), and u.

Referenced by phasing_move(), and walk_move().

◆ on_options_changed()

void game::on_options_changed ( )

Should be invoked whenever options change.

Definition at line 9792 of file game.cpp.

9793{
9794#if defined(TILES)
9795 tilecontext->on_options_changed();
9796#endif
9797 grid_tracker_ptr->on_options_changed();
9798}

References grid_tracker_ptr.

◆ open_consume_item_menu()

void game::open_consume_item_menu ( )
private

Definition at line 1503 of file handle_action.cpp.

1504{
1505 uilist as_m;
1506
1507 as_m.text = _( "What do you want to consume?" );
1508
1509 as_m.entries.emplace_back( 0, true, 'f', _( "Food" ) );
1510 as_m.entries.emplace_back( 1, true, 'd', _( "Drink" ) );
1511 as_m.entries.emplace_back( 2, true, 'm', _( "Medication" ) );
1512 as_m.query();
1513
1514 switch( as_m.ret ) {
1515 case 0:
1517 break;
1518 case 1:
1520 break;
1521 case 2:
1523 break;
1524 default:
1525 break;
1526 }
1527}
std::vector< uilist_entry > entries
Definition: ui.h:323
item_location consume_drink(player &p)
Consuming a drink item via a custom menu.
item_location consume_meds(player &p)
Consuming a medication item via a custom menu.
item_location consume_food(player &p)
Consuming a food item via a custom menu.

References _, game_menus::inv::consume_drink(), game_menus::inv::consume_food(), game_menus::inv::consume_meds(), avatar_action::eat(), uilist::entries, uilist::query(), uilist::ret, uilist::text, and u.

Referenced by handle_action().

◆ overmap_npc_move()

void game::overmap_npc_move ( )
private

Definition at line 4205 of file game.cpp.

4206{
4207 std::vector<npc *> travelling_npcs;
4208 static constexpr int move_search_radius = 600;
4209 for( auto &elem : overmap_buffer.get_npcs_near_player( move_search_radius ) ) {
4210 if( !elem ) {
4211 continue;
4212 }
4213 npc *npc_to_add = elem.get();
4214 if( ( !npc_to_add->is_active() || rl_dist( u.pos(), npc_to_add->pos() ) > SEEX * 2 ) &&
4215 npc_to_add->mission == NPC_MISSION_TRAVELLING ) {
4216 travelling_npcs.push_back( npc_to_add );
4217 }
4218 }
4219 for( auto &elem : travelling_npcs ) {
4220 if( elem->has_omt_destination() ) {
4221 if( !elem->omt_path.empty() && rl_dist( elem->omt_path.back(), elem->global_omt_location() ) > 2 ) {
4222 //recalculate path, we got distracted doing something else probably
4223 elem->omt_path.clear();
4224 }
4225 if( elem->omt_path.empty() ) {
4226 const tripoint_abs_omt &from = elem->global_omt_location();
4227 const tripoint_abs_omt &to = elem->goal;
4228 elem->omt_path = overmap_buffer.get_travel_path( elem->global_omt_location(), elem->goal,
4230 if( elem->omt_path.empty() ) {
4231 add_msg( m_debug, "%s couldn't find overmap path from %s to %s",
4232 elem->get_name(), from.to_string(), to.to_string() );
4233 elem->goal = npc::no_goal_point;
4234 elem->mission = NPC_MISSION_NULL;
4235 }
4236 } else {
4237 if( elem->omt_path.back() == elem->global_omt_location() ) {
4238 elem->omt_path.pop_back();
4239 }
4240 // TODO: fix point types
4241 elem->travel_overmap(
4242 project_to<coords::sm>( elem->omt_path.back() ).raw() );
4243 }
4244 reload_npcs();
4245 }
4246 }
4247 return;
4248}
std::vector< tripoint_abs_omt > omt_path
Route for overmap scale traveling.
Definition: character.h:1839
static constexpr tripoint_abs_omt no_goal_point
Definition: npc.h:1303
bool is_active() const
Definition: npc.cpp:2200
std::vector< tripoint_abs_omt > get_travel_path(const tripoint_abs_omt &src, const tripoint_abs_omt &dest, overmap_path_params params)
@ NPC_MISSION_NULL
Definition: npc.h:142
@ NPC_MISSION_TRAVELLING
Definition: npc.h:154
static overmap_path_params for_npc()

References add_msg(), overmap_path_params::for_npc(), overmapbuffer::get_npcs_near_player(), overmapbuffer::get_travel_path(), npc::is_active(), m_debug, npc::mission, npc::no_goal_point, NPC_MISSION_NULL, NPC_MISSION_TRAVELLING, Character::omt_path, overmap_buffer, Character::pos(), reload_npcs(), rl_dist(), SEEX, coords::coord_point< Point, Origin, Scale >::to_string(), and u.

Referenced by do_turn().

◆ peek() [1/2]

void game::peek ( )

Definition at line 5659 of file game.cpp.

5660{
5661 const std::optional<tripoint> p = choose_direction( _( "Peek where?" ), true );
5662 if( !p ) {
5663 return;
5664 }
5665
5666 if( p->z != 0 ) {
5667 const tripoint old_pos = u.pos();
5668 vertical_move( p->z, false, true );
5669
5670 if( old_pos != u.pos() ) {
5671 look_around();
5672 vertical_move( p->z * -1, false, true );
5673 }
5674 return;
5675 }
5676
5677 if( m.impassable( u.pos() + *p ) || m.obstructed_by_vehicle_rotation( u.pos(), u.pos() + *p ) ) {
5678 return;
5679 }
5680
5681 peek( u.pos() + *p );
5682}
std::optional< tripoint > choose_direction(const std::string &message, const bool allow_vertical)
Request player input of a direction, possibly including vertical component.
Definition: action.cpp:946

References _, choose_direction(), map::impassable(), look_around(), m, map::obstructed_by_vehicle_rotation(), peek(), Character::pos(), u, and vertical_move().

Referenced by handle_action(), and peek().

◆ peek() [2/2]

void game::peek ( const tripoint p)

Definition at line 5684 of file game.cpp.

5685{
5686 u.moves -= 200;
5687 tripoint prev = u.pos();
5688 u.setpos( p );
5689 tripoint center = p;
5690 const look_around_result result = look_around( /*show_window=*/true, center, center, false, false,
5691 true );
5692 u.setpos( prev );
5693
5694 if( result.peek_action && *result.peek_action == PA_BLIND_THROW ) {
5695 item_location loc;
5696 avatar_action::plthrow( u, loc, p );
5697 }
5699}

References center, map::invalidate_map_cache(), look_around(), m, Creature::moves, PA_BLIND_THROW, avatar_action::plthrow(), Character::pos(), Character::setpos(), u, and tripoint::z.

◆ perhaps_add_random_npc()

void game::perhaps_add_random_npc ( )
private

Definition at line 11100 of file game.cpp.

11101{
11102 static constexpr time_duration spawn_interval = 1_hours;
11103 if( !calendar::once_every( spawn_interval ) ) {
11104 return;
11105 }
11106 // Create a new NPC?
11107 // Only allow NPCs on 0 z-level, otherwise they can bug out due to lack of spots
11108 if( !get_option<bool>( "RANDOM_NPC" ) || ( !m.has_zlevels() && get_levz() != 0 ) ) {
11109 return;
11110 }
11111
11112 // We want the "NPC_DENSITY" to denote number of NPCs per week, per overmap, or so
11113 // But soft-cap it at about a standard year (4*14 days) worth
11114 const int npc_num = overmap_buffer.get_npcs_near_player(
11116 const double chance = npc_overmap::spawn_chance_in_hour( npc_num,
11117 get_option<float>( "NPC_DENSITY" ) );
11118 add_msg( m_debug, "Random NPC spawn chance %0.3f%%", chance * 100 );
11119 if( !x_in_y( chance, 1.0f ) ) {
11120 return;
11121 }
11122
11123 bool spawn_allowed = false;
11125 int counter = 0;
11126 while( !spawn_allowed ) {
11127 if( counter >= 100 ) {
11128 return;
11129 }
11130 // Shouldn't be larger than search radius or it might get swarmy at the edges
11131 static constexpr int radius_spawn_range = npc_overmap::density_search_radius;
11132 const tripoint_abs_omt u_omt = u.global_omt_location();
11133 spawn_point = u_omt + point( rng( -radius_spawn_range, radius_spawn_range ),
11134 rng( -radius_spawn_range, radius_spawn_range ) );
11135 spawn_point.z() = 0;
11136 const oter_id oter = overmap_buffer.ter( spawn_point );
11137 // Shouldn't spawn on lakes or rivers.
11138 // TODO: Prefer greater distance
11139 if( !is_river_or_lake( oter ) || rl_dist( u_omt.xy(), spawn_point.xy() ) < 30 ) {
11140 spawn_allowed = true;
11141 }
11142 counter += 1;
11143 }
11144 shared_ptr_fast<npc> tmp = make_shared_fast<npc>();
11145 tmp->randomize();
11146 std::string new_fac_id = "solo_";
11147 new_fac_id += tmp->name;
11148 // create a new "lone wolf" faction for this one NPC
11149 faction *new_solo_fac = faction_manager_ptr->add_new_faction( tmp->name, faction_id( new_fac_id ),
11150 faction_id( "no_faction" ) );
11151 tmp->set_fac( new_solo_fac ? new_solo_fac->id : faction_id( "no_faction" ) );
11152 // adds the npc to the correct overmap.
11153 // Only spawn random NPCs on z-level 0
11154 // TODO: fix point types
11155 tripoint submap_spawn = omt_to_sm_copy( spawn_point.raw() );
11156 tmp->spawn_at_sm( tripoint( submap_spawn.xy(), 0 ) );
11158 tmp->form_opinion( u );
11159 tmp->mission = NPC_MISSION_NULL;
11160 tmp->long_term_goal_action();
11161 tmp->add_new_mission( mission::reserve_random( ORIGIN_ANY_NPC, tmp->global_omt_location(),
11162 tmp->getID() ) );
11163 dbg( DL::Debug ) << "Spawning a random NPC at " << spawn_point;
11164 // This will make the new NPC active- if its nearby to the player
11165 load_npcs();
11166}
faction_id id
Definition: faction.h:83
point omt_to_sm_copy(point p)
@ Debug
Debug information (default: disabled).
@ ORIGIN_ANY_NPC
Definition: mission.h:46
double spawn_chance_in_hour(int current_npc_count, double density)
Chance that a random NPC spawns somewhere on overmap.
Definition: game.cpp:11089
static constexpr int density_search_radius
Radius of the area in which we count NPCs for random spawn chance.
Definition: npc.h:1423
bool is_river_or_lake(const oter_id &ter)
Definition: overmap.cpp:563

References add_msg(), dbg, Debug, npc_overmap::density_search_radius, faction_manager_ptr, get_levz(), overmapbuffer::get_npcs_near_player(), Character::global_omt_location(), map::has_zlevels(), faction_template::id, overmapbuffer::insert_npc(), is_river_or_lake(), load_npcs(), m, m_debug, NPC_MISSION_NULL, omt_to_sm_copy(), calendar::once_every(), ORIGIN_ANY_NPC, overmap_buffer, mission::reserve_random(), rl_dist(), rng(), npc_overmap::spawn_chance_in_hour(), overmapbuffer::ter(), u, x_in_y(), coords::coord_point< Point, Origin, Scale >::xy(), and tripoint::xy().

Referenced by do_turn().

◆ phasing_move()

bool game::phasing_move ( const tripoint dest,
bool  via_ramp = false 
)

Definition at line 9483 of file game.cpp.

9484{
9485 if( dest_loc.z != u.posz() && !via_ramp ) {
9486 // No vertical phasing yet
9487 return false;
9488 }
9489
9490 //probability travel through walls but not water
9491 tripoint dest = dest_loc;
9492 // tile is impassable
9493 int tunneldist = 0;
9494 const point d( sgn( dest.x - u.posx() ), sgn( dest.y - u.posy() ) );
9495 while( m.impassable( dest ) ||
9496 ( critter_at( dest ) != nullptr && tunneldist > 0 ) ) {
9497 //add 1 to tunnel distance for each impassable tile in the line
9498 tunneldist += 1;
9499 //Being dimensionally anchored prevents quantum shenanigans.
9500 if( u.worn_with_flag( "DIMENSIONAL_ANCHOR" ) || u.has_effect_with_flag( "DIMENSIONAL_ANCHOR" ) ) {
9502 _( "You try to quantum tunnel through the barrier, but something holds you back!" ) );
9503 return false;
9504 }
9505 if( tunneldist > 24 ) {
9506 add_msg( m_info, _( "It's too dangerous to tunnel that far!" ) );
9507 return false;
9508 }
9509
9510 dest.x += d.x;
9511 dest.y += d.y;
9512 }
9513
9515
9516 if( tunneldist != 0 ) {
9517 // -1 because power_cost for the first tile was already taken up by the bionic's activation
9518 if( ( tunneldist - 1 ) * power_cost > u.get_power_level() ) {
9519 // oops, not enough energy! Tunneling costs set amount of bionic power per impassable tile
9520 if( tunneldist * power_cost > u.get_max_power_level() ) {
9521 add_msg( _( "You try to quantum tunnel through the barrier but bounce off! You don't have enough bionic power capacity to travel that far." ) );
9522 } else {
9523 add_msg( _( "You try to quantum tunnel through the barrier but are reflected! You need %s of bionic power to travel that thickness of material." ),
9524 units::display( power_cost * tunneldist ) );
9525 }
9526 return false;
9527 }
9528
9529 if( u.in_vehicle ) {
9530 m.unboard_vehicle( u.pos() );
9531 }
9532
9533 add_msg( _( "You quantum tunnel through the %d-tile wide barrier!" ), tunneldist );
9534 //tunneling costs 100 bionic power per impassable tile, but the first 100 was already drained by activation.
9535 u.mod_power_level( -( ( tunneldist - 1 ) * power_cost ) );
9536 //tunneling costs 100 moves baseline, 50 per extra tile up to a cap of 500 moves
9537 u.moves -= ( 50 + ( tunneldist * 50 ) );
9538 u.setpos( dest );
9539
9540 if( m.veh_at( u.pos() ).part_with_feature( "BOARDABLE", true ) ) {
9541 m.board_vehicle( u.pos(), &u );
9542 }
9543
9544 u.grab( OBJECT_NONE );
9546 m.creature_on_trap( u );
9547 return true;
9548 }
9549
9550 return false;
9551}
bool worn_with_flag(const std::string &flag, const bodypart_id &bp=bodypart_str_id::NULL_ID()) const
Returns true if the player is wearing an item with the given flag.
Definition: character.cpp:3265
units::energy get_max_power_level() const
Definition: character.cpp:1910
bool has_effect_with_flag(const std::string &flag, body_part bp=num_bp) const
Check if creature has any effect with the given flag.
Definition: creature.cpp:1229
void on_move_effects()
Definition: game.cpp:9758
void board_vehicle(const tripoint &p, player *pl)
Definition: map.cpp:1114
constexpr int sgn(const T x)
Definition: enums.h:8
static const bionic_id bio_probability_travel("bio_probability_travel")
std::string display(const units::energy v)
Definition: units.cpp:59
units::energy power_activate
Power cost on activation.
Definition: bionics.h:37

References _, add_msg(), player::add_msg_if_player(), bio_probability_travel, map::board_vehicle(), map::creature_on_trap(), critter_at(), anonymous_namespace{iexamine_elevator.cpp}::elevator::dest(), units::display(), Character::get_max_power_level(), Character::get_power_level(), avatar::grab(), Creature::has_effect_with_flag(), map::impassable(), Character::in_vehicle, m, m_info, Character::mod_power_level(), Creature::moves, OBJECT_NONE, on_move_effects(), Character::pos(), Character::posx(), Character::posy(), Character::posz(), bionic_data::power_activate, Character::setpos(), sgn(), u, map::unboard_vehicle(), map::veh_at(), Character::worn_with_flag(), point::x, point::y, and tripoint::z.

◆ pickup() [1/2]

void game::pickup ( )
private

Definition at line 5630 of file game.cpp.

5631{
5632 const std::optional<tripoint> examp_ = choose_adjacent_highlight( _( "Pickup where?" ),
5633 _( "There is nothing to pick up nearby." ),
5634 ACTION_PICKUP, false );
5635 if( !examp_ ) {
5636 return;
5637 }
5638 pickup( *examp_ );
5639}

References _, ACTION_PICKUP, choose_adjacent_highlight(), and pickup().

Referenced by handle_action(), and pickup().

◆ pickup() [2/2]

void game::pickup ( const tripoint p)
private

Definition at line 5641 of file game.cpp.

5642{
5643 // Highlight target
5644 shared_ptr_fast<game::draw_callback_t> hilite_cb = make_shared_fast<game::draw_callback_t>( [&]() {
5645 m.drawsq( w_terrain, p, drawsq_params().highlight( true ) );
5646 } );
5647 add_draw_callback( hilite_cb );
5648
5649 pickup::pick_up( p, 0 );
5650}

References add_draw_callback(), map::drawsq(), m, pickup::pick_up(), and w_terrain.

◆ pickup_feet()

void game::pickup_feet ( )
private

Definition at line 5652 of file game.cpp.

5653{
5654 pickup::pick_up( u.pos(), 1 );
5655}

References pickup::pick_up(), Character::pos(), and u.

Referenced by handle_action().

◆ place_critter_around() [1/2]

monster * game::place_critter_around ( const mtype_id id,
const tripoint center,
int  radius 
)

Definition at line 4673 of file game.cpp.

4674{
4675 // TODO: change this into an assert, it must never happen.
4676 if( id.is_null() ) {
4677 return nullptr;
4678 }
4679 return place_critter_around( make_shared_fast<monster>( id ), center, radius );
4680}
monster * place_critter_around(const mtype_id &id, const tripoint &center, int radius)
Definition: game.cpp:4673

References center, and place_critter_around().

Referenced by place_critter_around(), place_critter_at(), replace_stair_monsters(), and start_game().

◆ place_critter_around() [2/2]

monster * game::place_critter_around ( const shared_ptr_fast< monster > &  mon,
const tripoint center,
int  radius,
bool  forced = false 
)

Definition at line 4682 of file game.cpp.

4686{
4687 std::optional<tripoint> where;
4688 if( forced || can_place_monster( *mon, center ) ) {
4689 where = center;
4690 }
4691
4692 // This loop ensures the monster is placed as close to the center as possible,
4693 // but all places that equally far from the center have the same probability.
4694 for( int r = 1; r <= radius && !where; ++r ) {
4696 }
4697
4698 if( !where ) {
4699 return nullptr;
4700 }
4701 mon->spawn( *where );
4702 return critter_tracker->add( mon ) ? mon.get() : nullptr;
4703}
static std::optional< tripoint > choose_where_to_place_monster(const monster &mon, const tripoint_range< tripoint > &range)
Definition: game.cpp:4655
static bool can_place_monster(const monster &mon, const tripoint &p)
Definition: game.cpp:4639

References can_place_monster(), center, choose_where_to_place_monster(), critter_tracker, m, and map::points_in_radius().

◆ place_critter_at() [1/2]

monster * game::place_critter_at ( const mtype_id id,
const tripoint p 
)

Adds critters to the reality bubble, creating them if necessary.

Functions taking a id parameter will construct a monster based on that id, (with default properties). Functions taking a mon parameter will use the supplied monster instance instead (which must not be null). Note: the monster will not be upgraded by these functions, it is placed as is.

place_critter_at will place the creature exactly at the given point.

place_critter_around will place the creature around the center p within the given radius (radius 0 means only the center point is used). The chosen point will be as close to the center as possible.

place_critter_within will place the creature at a random point within that given range. (All points within have equal probability.)

Returns
All functions return null if the creature could not be placed (usually because the target is not suitable for it: may be a solid wall, or air, or already occupied by some creature). If the creature has been placed, it returns a pointer to it (which is the same as the one contained in mon).

Definition at line 4663 of file game.cpp.

4664{
4665 return place_critter_around( id, p, 0 );
4666}

References place_critter_around().

Referenced by fungal_effects::fungalize(), revive_corpse(), fungal_effects::spread_fungus_one_tile(), and update_stair_monsters().

◆ place_critter_at() [2/2]

monster * game::place_critter_at ( const shared_ptr_fast< monster > &  mon,
const tripoint p 
)

Definition at line 4668 of file game.cpp.

4669{
4670 return place_critter_around( mon, p, 0 );
4671}

References place_critter_around().

◆ place_critter_within() [1/2]

monster * game::place_critter_within ( const mtype_id id,
const tripoint_range< tripoint > &  range 
)

Definition at line 4705 of file game.cpp.

4706{
4707 // TODO: change this into an assert, it must never happen.
4708 if( id.is_null() ) {
4709 return nullptr;
4710 }
4711 return place_critter_within( make_shared_fast<monster>( id ), range );
4712}
monster * place_critter_within(const mtype_id &id, const tripoint_range< tripoint > &range)
Definition: game.cpp:4705

References place_critter_within(), and range.

Referenced by place_critter_within().

◆ place_critter_within() [2/2]

monster * game::place_critter_within ( const shared_ptr_fast< monster > &  mon,
const tripoint_range< tripoint > &  range 
)

Definition at line 4714 of file game.cpp.

4716{
4717 const std::optional<tripoint> where = choose_where_to_place_monster( *mon, range );
4718 if( !where ) {
4719 return nullptr;
4720 }
4721 mon->spawn( *where );
4722 return critter_tracker->add( mon ) ? mon.get() : nullptr;
4723}

References choose_where_to_place_monster(), critter_tracker, and range.

◆ place_player()

point game::place_player ( const tripoint dest)
Dexterity increases chance of avoiding cuts on sharp terrain

Definition at line 9121 of file game.cpp.

9122{
9123 const optional_vpart_position vp1 = m.veh_at( dest_loc );
9124 if( const std::optional<std::string> label = vp1.get_label() ) {
9125 add_msg( m_info, _( "Label here: %s" ), *label );
9126 }
9127 std::string signage = m.get_signage( dest_loc );
9128 if( !signage.empty() ) {
9129 if( !u.has_trait( trait_ILLITERATE ) ) {
9130 add_msg( m_info, _( "The sign says: %s" ), signage );
9131 } else {
9132 add_msg( m_info, _( "There is a sign here, but you are unable to read it." ) );
9133 }
9134 }
9135 if( m.has_graffiti_at( dest_loc ) ) {
9136 if( !u.has_trait( trait_ILLITERATE ) ) {
9137 add_msg( m_info, _( "Written here: %s" ), m.graffiti_at( dest_loc ) );
9138 } else {
9139 add_msg( m_info, _( "Something is written here, but you are unable to read it." ) );
9140 }
9141 }
9142 // TODO: Move the stuff below to a Character method so that NPCs can reuse it
9143 if( m.has_flag( "ROUGH", dest_loc ) && ( !u.in_vehicle ) && ( !u.is_mounted() ) ) {
9144 if( one_in( 5 ) && u.get_armor_bash( bodypart_id( "foot_l" ) ) < rng( 2, 5 ) ) {
9145 add_msg( m_bad, _( "You hurt your left foot on the %s!" ),
9146 m.has_flag_ter( "ROUGH", dest_loc ) ? m.tername( dest_loc ) : m.furnname(
9147 dest_loc ) );
9148 u.deal_damage( nullptr, bodypart_id( "foot_l" ), damage_instance( DT_CUT, 1 ) );
9149 }
9150 if( one_in( 5 ) && u.get_armor_bash( bodypart_id( "foot_r" ) ) < rng( 2, 5 ) ) {
9151 add_msg( m_bad, _( "You hurt your right foot on the %s!" ),
9152 m.has_flag_ter( "ROUGH", dest_loc ) ? m.tername( dest_loc ) : m.furnname(
9153 dest_loc ) );
9154 u.deal_damage( nullptr, bodypart_id( "foot_l" ), damage_instance( DT_CUT, 1 ) );
9155 }
9156 }
9157 ///\EFFECT_DEX increases chance of avoiding cuts on sharp terrain
9158 if( m.has_flag( "SHARP", dest_loc ) && !one_in( 3 ) && !x_in_y( 1 + u.dex_cur / 2.0, 40 ) &&
9159 ( !u.in_vehicle && !m.veh_at( dest_loc ) ) && ( !u.has_trait( trait_PARKOUR ) ||
9160 one_in( 4 ) ) && ( u.has_trait( trait_THICKSKIN ) ? !one_in( 8 ) : true ) ) {
9161 if( u.is_mounted() ) {
9162 add_msg( _( "Your %s gets cut!" ), u.mounted_creature->get_name() );
9163 u.mounted_creature->apply_damage( nullptr, bodypart_id( "torso" ), rng( 1, 10 ) );
9164 } else {
9165 const bodypart_id bp = u.get_random_body_part();
9166 if( u.deal_damage( nullptr, bp, damage_instance( DT_CUT, rng( 1, 10 ) ) ).total_damage() > 0 ) {
9167 //~ 1$s - bodypart name in accusative, 2$s is terrain name.
9168 add_msg( m_bad, _( "You cut your %1$s on the %2$s!" ),
9169 body_part_name_accusative( bp->token ),
9170 m.has_flag_ter( "SHARP", dest_loc ) ? m.tername( dest_loc ) : m.furnname(
9171 dest_loc ) );
9172 }
9173 }
9174 }
9175 if( m.has_flag( "UNSTABLE", dest_loc ) && !u.is_mounted() ) {
9176 u.add_effect( effect_bouldering, 1_turns, num_bp );
9177 } else if( u.has_effect( effect_bouldering ) ) {
9179 }
9180 if( m.has_flag_ter_or_furn( TFLAG_NO_SIGHT, dest_loc ) ) {
9181 u.add_effect( effect_no_sight, 1_turns, num_bp );
9182 } else if( u.has_effect( effect_no_sight ) ) {
9184 }
9185
9186 // If we moved out of the nonant, we need update our map data
9187 if( m.has_flag( "SWIMMABLE", dest_loc ) && u.has_effect( effect_onfire ) ) {
9188 add_msg( _( "The water puts out the flames!" ) );
9190 if( u.is_mounted() ) {
9191 monster *mon = u.mounted_creature.get();
9192 if( mon->has_effect( effect_onfire ) ) {
9194 }
9195 }
9196 }
9197
9198 if( monster *const mon_ptr = critter_at<monster>( dest_loc ) ) {
9199 // We displaced a monster. It's probably a bug if it wasn't a friendly mon...
9200 // Immobile monsters can't be displaced.
9201 monster &critter = *mon_ptr;
9202 // TODO: handling for ridden creatures other than players mount.
9203 if( !critter.has_effect( effect_ridden ) ) {
9204 if( u.is_mounted() ) {
9205 std::vector<tripoint> valid;
9206 for( const tripoint &jk : m.points_in_radius( critter.pos(), 1 ) ) {
9207 if( is_empty( jk ) ) {
9208 valid.push_back( jk );
9209 }
9210 }
9211 if( !valid.empty() ) {
9212 critter.move_to( random_entry( valid ) );
9213 add_msg( _( "You push the %s out of the way." ), critter.name() );
9214 } else {
9215 add_msg( _( "There is no room to push the %s out of the way." ), critter.name() );
9216 return u.pos().xy();
9217 }
9218 } else {
9219 critter.move_to( u.pos(), false,
9220 true ); // Force the movement even though the player is there right now.
9221 add_msg( _( "You displace the %s." ), critter.name() );
9222 }
9223 } else if( !u.has_effect( effect_riding ) ) {
9224 add_msg( _( "You cannot move the %s out of the way." ), critter.name() );
9225 return u.pos().xy();
9226 }
9227 }
9228
9229 // If the player is in a vehicle, unboard them from the current part
9230 if( u.in_vehicle ) {
9231 m.unboard_vehicle( u.pos() );
9232 }
9233 // Move the player
9234 // Start with z-level, to make it less likely that old functions (2D ones) freak out
9235 if( m.has_zlevels() && dest_loc.z != get_levz() ) {
9236 vertical_shift( dest_loc.z );
9237 }
9238
9239 if( u.is_hauling() && ( !m.can_put_items( dest_loc ) ||
9240 m.has_flag( TFLAG_DEEP_WATER, dest_loc ) ||
9241 vp1 ) ) {
9242 u.stop_hauling();
9243 }
9244 u.setpos( dest_loc );
9245 if( u.is_mounted() ) {
9246 monster *mon = u.mounted_creature.get();
9247 mon->setpos( dest_loc );
9248 mon->process_triggers();
9249 m.creature_in_field( *mon );
9250 }
9251 point submap_shift = update_map( u );
9252 // Important: don't use dest_loc after this line. `update_map` may have shifted the map
9253 // and dest_loc was not adjusted and therefore is still in the un-shifted system and probably wrong.
9254 // If you must use it you can calculate the position in the new, shifted system with
9255 // adjusted_pos = ( old_pos.x - submap_shift.x * SEEX, old_pos.y - submap_shift.y * SEEY, old_pos.z )
9256
9257 //Auto pulp or butcher and Auto foraging
9258 if( get_option<bool>( "AUTO_FEATURES" ) && mostseen == 0 && !u.is_mounted() ) {
9260
9261 const std::string forage_type = get_option<std::string>( "AUTO_FORAGING" );
9262 if( forage_type != "off" ) {
9263 const auto forage = [&]( const tripoint & pos ) {
9264 const auto &xter_t = m.ter( pos ).obj().examine;
9265 const auto &xfurn_t = m.furn( pos ).obj().examine;
9266 const bool forage_everything = forage_type == "both";
9267 const bool forage_bushes = forage_everything || forage_type == "bushes";
9268 const bool forage_trees = forage_everything || forage_type == "trees";
9269 if( xter_t == &iexamine::none && xfurn_t == &iexamine::none ) {
9270 return;
9271 } else if( ( forage_bushes && xter_t == &iexamine::shrub_marloss ) ||
9272 ( forage_bushes && xter_t == &iexamine::shrub_wildveggies ) ||
9273 ( forage_bushes && xter_t == &iexamine::harvest_ter_nectar ) ||
9274 ( forage_trees && xter_t == &iexamine::tree_marloss ) ||
9275 ( forage_trees && xter_t == &iexamine::harvest_ter ) ||
9276 ( forage_trees && xter_t == &iexamine::harvest_ter_nectar )
9277 ) {
9278 xter_t( u, pos );
9279 } else if( ( forage_everything && xfurn_t == &iexamine::harvest_furn ) ||
9280 ( forage_everything && xfurn_t == &iexamine::harvest_furn_nectar )
9281 ) {
9282 xfurn_t( u, pos );
9283 }
9284 };
9285
9286 for( auto &elem : adjacentDir ) {
9287 forage( u.pos() + direction_XY( elem ) );
9288 }
9289 }
9290
9291 const std::string pulp_butcher = get_option<std::string>( "AUTO_PULP_BUTCHER" );
9292 if( pulp_butcher == "butcher" && u.max_quality( quality_id( "BUTCHER" ) ) > INT_MIN ) {
9293 std::vector<item *> corpses;
9294
9295 for( item &it : m.i_at( u.pos() ) ) {
9296 corpses.push_back( &it );
9297 }
9298
9299 if( !corpses.empty() ) {
9300 u.assign_activity( activity_id( "ACT_BUTCHER" ), 0, true );
9301 for( item *it : corpses ) {
9302 u.activity.targets.emplace_back( map_cursor( u.pos() ), it );
9303 }
9304 }
9305 } else if( pulp_butcher == "pulp" || pulp_butcher == "pulp_adjacent" ) {
9306 const auto pulp = [&]( const tripoint & pos ) {
9307 for( const auto &maybe_corpse : m.i_at( pos ) ) {
9308 if( maybe_corpse.is_corpse() && maybe_corpse.can_revive() &&
9309 !maybe_corpse.get_mtype()->bloodType().obj().has_acid ) {
9311 u.activity.placement = m.getabs( pos );
9312 u.activity.auto_resume = true;
9313 u.activity.str_values.push_back( "auto_pulp_no_acid" );
9314 return;
9315 }
9316 }
9317 };
9318
9319 if( pulp_butcher == "pulp_adjacent" ) {
9320 for( auto &elem : adjacentDir ) {
9321 pulp( u.pos() + direction_XY( elem ) );
9322 }
9323 } else {
9324 pulp( u.pos() );
9325 }
9326 }
9327 }
9328
9329 //Autopickup
9330 if( !u.is_mounted() && get_option<bool>( "AUTO_PICKUP" ) && !u.is_hauling() &&
9331 ( !get_option<bool>( "AUTO_PICKUP_SAFEMODE" ) || mostseen == 0 ) &&
9332 ( m.has_items( u.pos() ) || get_option<bool>( "AUTO_PICKUP_ADJACENT" ) ) ) {
9333 pickup::pick_up( u.pos(), -1 );
9334 }
9335
9336 // If the new tile is a boardable part, board it
9337 if( vp1.part_with_feature( "BOARDABLE", true ) && !u.is_mounted() ) {
9338 m.board_vehicle( u.pos(), &u );
9339 }
9340
9341 // Traps!
9342 // Try to detect.
9344 if( u.is_mounted() ) {
9346 } else {
9347 m.creature_on_trap( u );
9348 }
9349 // Drench the player if swimmable
9350 if( m.has_flag( "SWIMMABLE", u.pos() ) &&
9351 !( u.is_mounted() || ( u.in_vehicle && vp1->vehicle().can_float() ) ) ) {
9352 u.drench( 40, { { bp_foot_l, bp_foot_r, bp_leg_l, bp_leg_r } }, false );
9353 }
9354
9355 // List items here
9356 if( !m.has_flag( "SEALED", u.pos() ) ) {
9357 if( get_option<bool>( "NO_AUTO_PICKUP_ZONES_LIST_ITEMS" ) ||
9358 !check_zone( zone_type_id( "NO_AUTO_PICKUP" ), u.pos() ) ) {
9359 if( u.is_blind() && !m.i_at( u.pos() ).empty() ) {
9360 add_msg( _( "There's something here, but you can't see what it is." ) );
9361 } else if( m.has_items( u.pos() ) ) {
9362 std::vector<std::string> names;
9363 std::vector<size_t> counts;
9364 std::vector<item> items;
9365 for( auto &tmpitem : m.i_at( u.pos() ) ) {
9366
9367 std::string next_tname = tmpitem.tname();
9368 std::string next_dname = tmpitem.display_name();
9369 bool by_charges = tmpitem.count_by_charges();
9370 bool got_it = false;
9371 for( size_t i = 0; i < names.size(); ++i ) {
9372 if( by_charges && next_tname == names[i] ) {
9373 counts[i] += tmpitem.charges;
9374 got_it = true;
9375 break;
9376 } else if( next_dname == names[i] ) {
9377 counts[i] += 1;
9378 got_it = true;
9379 break;
9380 }
9381 }
9382 if( !got_it ) {
9383 if( by_charges ) {
9384 names.push_back( tmpitem.tname( tmpitem.charges ) );
9385 counts.push_back( tmpitem.charges );
9386 } else {
9387 names.push_back( tmpitem.display_name( 1 ) );
9388 counts.push_back( 1 );
9389 }
9390 items.push_back( tmpitem );
9391 }
9392 if( names.size() > 10 ) {
9393 break;
9394 }
9395 }
9396 for( size_t i = 0; i < names.size(); ++i ) {
9397 if( !items[i].count_by_charges() ) {
9398 names[i] = items[i].display_name( counts[i] );
9399 } else {
9400 names[i] = items[i].tname( counts[i] );
9401 }
9402 }
9403 int and_the_rest = 0;
9404 for( size_t i = 0; i < names.size(); ++i ) {
9405 //~ number of items: "<number> <item>"
9406 std::string fmt = vgettext( "%1$d %2$s", "%1$d %2$s", counts[i] );
9407 names[i] = string_format( fmt, counts[i], names[i] );
9408 // Skip the first two.
9409 if( i > 1 ) {
9410 and_the_rest += counts[i];
9411 }
9412 }
9413 if( names.size() == 1 ) {
9414 add_msg( _( "You see here %s." ), names[0] );
9415 } else if( names.size() == 2 ) {
9416 add_msg( _( "You see here %s and %s." ), names[0], names[1] );
9417 } else if( names.size() == 3 ) {
9418 add_msg( _( "You see here %s, %s, and %s." ), names[0], names[1], names[2] );
9419 } else if( and_the_rest < 7 ) {
9420 add_msg( vgettext( "You see here %s, %s and %d more item.",
9421 "You see here %s, %s and %d more items.",
9422 and_the_rest ),
9423 names[0], names[1], and_the_rest );
9424 } else {
9425 add_msg( _( "You see here %s and many more items." ), names[0] );
9426 }
9427 }
9428 }
9429 }
9430
9431 if( ( vp1.part_with_feature( "CONTROL_ANIMAL", true ) ||
9432 vp1.part_with_feature( "CONTROLS", true ) ) && u.in_vehicle && !u.is_mounted() ) {
9433 add_msg( _( "There are vehicle controls here." ) );
9434 if( !u.has_trait( trait_id( "WAYFARER" ) ) ) {
9435 add_msg( m_info, _( "%s to drive." ), press_x( ACTION_CONTROL_VEHICLE ) );
9436 }
9437 } else if( vp1.part_with_feature( "CONTROLS", true ) && u.in_vehicle &&
9438 u.is_mounted() ) {
9439 add_msg( _( "There are vehicle controls here but you cannot reach them whilst mounted." ) );
9440 }
9441 return submap_shift;
9442}
std::string body_part_name_accusative(body_part bp, int number)
Returns the matching accusative name of the body_part token, i.e.
Definition: bodypart.cpp:331
void drench(int saturation, const body_part_set &flags, bool ignore_waterproof)
Drenches the player with water, saturation is the percent gotten wet.
Definition: suffer.cpp:1824
bool is_hauling() const
Definition: character.cpp:9187
void stop_hauling()
Definition: character.cpp:9178
bodypart_id get_random_body_part(bool main=false) const
Definition: creature.cpp:1667
void vertical_shift(int z_after)
Actual z-level movement part of vertical_move.
Definition: game.cpp:10612
bool check_zone(const zone_type_id &type, const tripoint &where) const
Definition: game.cpp:6045
std::string furnname(const tripoint &p)
Definition: map.cpp:1534
bool has_flag_ter_or_furn(const std::string &flag, const tripoint &p) const
Definition: map.cpp:2404
bool has_graffiti_at(const tripoint &p) const
Definition: map.cpp:7980
bool has_items(const tripoint &p) const
Checks for existence of items.
Definition: map.cpp:4891
const std::string & graffiti_at(const tripoint &p) const
Definition: map.cpp:7969
bool has_flag_ter(const std::string &flag, const tripoint &p) const
Definition: map.cpp:2394
bool can_put_items(const tripoint &p) const
Definition: map.cpp:2380
void setpos(const tripoint &p) override
Definition: monster.cpp:234
bool move_to(const tripoint &p, bool force=false, bool step_on_critter=false, float stagger_adjustment=1.0)
Attempt to move to p.
Definition: monmove.cpp:1561
void process_triggers()
Definition: monster.cpp:1238
std::optional< std::string > get_label() const
std::vector< std::string > str_values
bool auto_resume
If true, the activity will be auto-resumed next time the player attempts an identical activity.
static const efftype_id effect_riding("riding")
static const trait_id trait_ILLITERATE("ILLITERATE")
static const efftype_id effect_bouldering("bouldering")
static const trait_id trait_PARKOUR("PARKOUR")
static const efftype_id effect_no_sight("no_sight")
static const trait_id trait_THICKSKIN("THICKSKIN")
static const efftype_id effect_onfire("onfire")
point direction_XY(const direction dir)
Definition: line.cpp:433
@ TFLAG_NO_SIGHT
Definition: mapdata.h:284
@ TFLAG_DEEP_WATER
Definition: mapdata.h:302
static std::map< nameFlags, std::vector< std::string > > names
Definition: name.cpp:18
const int INDEFINITELY_LONG
A number that represents the longest possible action.
void search_surroundings(Character &who)
Search surrounding squares for traps (and maybe other things in the future).
void shrub_wildveggies(player &p, const tripoint &examp)
Definition: iexamine.cpp:3599
void shrub_marloss(player &p, const tripoint &examp)
Definition: iexamine.cpp:3564
void harvest_ter(player &p, const tripoint &examp)
Definition: iexamine.cpp:2036
void harvest_furn(player &p, const tripoint &examp)
Definition: iexamine.cpp:2015
void harvest_ter_nectar(player &p, const tripoint &examp)
Definition: iexamine.cpp:2024
void harvest_furn_nectar(player &p, const tripoint &examp)
Definition: iexamine.cpp:2006
void tree_marloss(player &p, const tripoint &examp)
Definition: iexamine.cpp:3578
string_id< zone_type > zone_type_id
Definition: type_id.h:202

References _, ACTION_CONTROL_VEHICLE, Character::activity, Creature::add_effect(), add_msg(), Character::assign_activity(), player_activity::auto_resume, map::board_vehicle(), body_part_name_accusative(), bp_foot_l, bp_foot_r, bp_leg_l, bp_leg_r, map::can_put_items(), check_zone(), map::creature_in_field(), map::creature_on_trap(), Character::deal_damage(), Character::dex_cur, direction_XY(), Character::drench(), DT_CUT, EAST, effect_bouldering, effect_no_sight, effect_onfire, effect_ridden, effect_riding, item_stack::empty(), map_data_common_t::examine, map::furn(), map::furnname(), Character::get_armor_bash(), optional_vpart_position::get_label(), get_levz(), Creature::get_random_body_part(), map::get_signage(), map::getabs(), map::graffiti_at(), iexamine::harvest_furn(), iexamine::harvest_furn_nectar(), iexamine::harvest_ter(), iexamine::harvest_ter_nectar(), Creature::has_effect(), map::has_flag(), map::has_flag_ter(), map::has_flag_ter_or_furn(), map::has_graffiti_at(), map::has_items(), Character::has_trait(), map::has_zlevels(), map::i_at(), Character::in_vehicle, calendar::INDEFINITELY_LONG, Character::is_blind(), is_empty(), Character::is_hauling(), Character::is_mounted(), m, m_bad, m_info, visitable< T >::max_quality(), mostseen, Character::mounted_creature, monster::move_to(), monster::name(), Name::names, iexamine::none(), NORTH, NORTHEAST, NORTHWEST, num_bp, int_id< T >::obj(), one_in(), optional_vpart_position::part_with_feature(), pickup::pick_up(), player_activity::placement, map::points_in_radius(), Character::pos(), monster::pos(), press_x(), monster::process_triggers(), random_entry(), Creature::remove_effect(), rng(), character_funcs::search_surroundings(), Character::setpos(), monster::setpos(), iexamine::shrub_marloss(), iexamine::shrub_wildveggies(), SOUTH, SOUTHEAST, SOUTHWEST, Character::stop_hauling(), player_activity::str_values, string_format(), player_activity::targets, map::ter(), map::tername(), TFLAG_DEEP_WATER, TFLAG_NO_SIGHT, trait_ILLITERATE, trait_PARKOUR, trait_THICKSKIN, iexamine::tree_marloss(), u, map::unboard_vehicle(), update_map(), map::veh_at(), vertical_shift(), vgettext(), WEST, x_in_y(), tripoint::xy(), and tripoint::z.

Referenced by place_player_overmap(), and walk_move().

◆ place_player_overmap()

void game::place_player_overmap ( const tripoint_abs_omt om_dest)

Definition at line 9444 of file game.cpp.

9445{
9446 // if player is teleporting around, they don't bring their horse with them
9447 if( u.is_mounted() ) {
9449 u.mounted_creature->remove_effect( effect_ridden );
9450 u.mounted_creature = nullptr;
9451 }
9452 // offload the active npcs.
9453 unload_npcs();
9454 for( monster &critter : all_monsters() ) {
9455 despawn_monster( critter );
9456 }
9457 if( u.in_vehicle ) {
9458 m.unboard_vehicle( u.pos() );
9459 }
9460
9462 const int minz = m.has_zlevels() ? -OVERMAP_DEPTH : get_levz();
9463 const int maxz = m.has_zlevels() ? OVERMAP_HEIGHT : get_levz();
9464 for( int z = minz; z <= maxz; z++ ) {
9465 m.clear_vehicle_list( z );
9466 }
9468 // offset because load_map expects the coordinates of the top left corner, but the
9469 // player will be centered in the middle of the map.
9470 // TODO: fix point types
9471 const tripoint map_sm_pos(
9472 project_to<coords::sm>( om_dest ).raw() + point( -HALF_MAPSIZE, -HALF_MAPSIZE ) );
9473 const tripoint player_pos( u.pos().xy(), map_sm_pos.z );
9474 load_map( map_sm_pos );
9475 load_npcs();
9476 m.spawn_monsters( true ); // Static monsters
9478 // update weather now as it could be different on the new location
9480 place_player( player_pos );
9481}
point place_player(const tripoint &dest)
Definition: game.cpp:9121
void unload_npcs()
Unloads all NPCs.
Definition: game.cpp:871
void update_overmap_seen()
Definition: game.cpp:10790
level_cache & access_cache(int zlev)
Definition: map.cpp:8890
void clear_vehicle_list(int zlev)
Definition: map.cpp:391
void clear_vehicle_cache()
Definition: map.cpp:373
std::bitset< MAPSIZE_X *MAPSIZE_Y > map_memory_seen_cache
Definition: map.h:351

References map::access_cache(), all_monsters(), map::clear_vehicle_cache(), map::clear_vehicle_list(), despawn_monster(), effect_ridden, effect_riding, get_levz(), get_weather, HALF_MAPSIZE, map::has_zlevels(), Character::in_vehicle, Character::is_mounted(), load_map(), load_npcs(), m, level_cache::map_memory_seen_cache, Character::mounted_creature, weather_manager::nextweather, OVERMAP_DEPTH, OVERMAP_HEIGHT, place_player(), Character::pos(), Creature::remove_effect(), map::spawn_monsters(), calendar::turn, u, map::unboard_vehicle(), unload_npcs(), update_overmap_seen(), tripoint::xy(), and tripoint::z.

◆ place_vehicle_nearby()

vehicle * game::place_vehicle_nearby ( const vproto_id id,
const point_abs_omt origin,
int  min_distance,
int  max_distance,
const std::vector< std::string > &  omt_search_types = {} 
)
private

Definition at line 767 of file game.cpp.

770{
771 std::vector<std::string> search_types = omt_search_types;
772 if( search_types.empty() ) {
773 vehicle veh( id );
774 if( veh.can_float() ) {
775 search_types.push_back( "river" );
776 search_types.push_back( "lake" );
777 } else {
778 search_types.push_back( "field" );
779 search_types.push_back( "road" );
780 }
781 }
782 for( const std::string &search_type : search_types ) {
783 omt_find_params find_params;
784 find_params.must_see = false;
785 find_params.cant_see = false;
786 find_params.types.emplace_back( search_type, ot_match_type::type );
787 // find nearest road
788 find_params.min_distance = min_distance;
789 find_params.search_range = max_distance;
790 // if player spawns underground, park their car on the surface.
791 const tripoint_abs_omt omt_origin( origin, 0 );
792 for( const tripoint_abs_omt &goal : overmap_buffer.find_all( omt_origin, find_params ) ) {
793 // try place vehicle there.
794 tinymap target_map;
795 target_map.load( project_to<coords::sm>( goal ), false );
796 const tripoint tinymap_center( SEEX, SEEY, goal.z() );
797 static constexpr std::array<units::angle, 4> angles = {{
798 0_degrees, 90_degrees, 180_degrees, 270_degrees
799 }
800 };
801 vehicle *veh = target_map.add_vehicle(
802 id, tinymap_center, random_entry( angles ), rng( 50, 80 ), 0, false );
803 if( veh ) {
804 tripoint abs_local = m.getlocal( target_map.getabs( tinymap_center ) );
805 veh->sm_pos = ms_to_sm_remain( abs_local );
806 veh->pos = abs_local.xy();
808 veh->tracking_on = true;
809 target_map.save();
810 return veh;
811 }
812 }
813 }
814 return nullptr;
815}
void save()
Add currently loaded submaps (in grid) to the mapbuffer.
Definition: map.cpp:6735
vehicle * add_vehicle(const vgroup_id &type, const tripoint &p, units::angle dir, int init_veh_fuel=-1, int init_veh_status=-1, bool merge_wrecks=true)
Definition: mapgen.cpp:5438
void add_vehicle(vehicle *veh)
Add the vehicle to be tracked in the overmap.
std::vector< tripoint_abs_omt > find_all(const tripoint_abs_omt &origin, const omt_find_params &params)
Find all places with the specific overmap terrain type.
Definition: map.h:2065
point pos
Position of the vehicle inside the submap that contains the vehicle.
Definition: vehicle.h:1648
tripoint sm_pos
Submap coordinates of the currently loaded submap (see game::m) that contains this vehicle.
Definition: vehicle.h:1633
bool tracking_on
Definition: vehicle.h:1723
point ms_to_sm_remain(int &x, int &y)
static constexpr int SEEY
Standard arguments for finding overmap terrain.
std::vector< std::pair< std::string, ot_match_type > > types

References map::add_vehicle(), overmapbuffer::add_vehicle(), vehicle::can_float(), omt_find_params::cant_see, overmapbuffer::find_all(), map::getabs(), map::getlocal(), map::load(), m, omt_find_params::min_distance, ms_to_sm_remain(), omt_find_params::must_see, overmap_buffer, vehicle::pos, random_entry(), rng(), map::save(), omt_find_params::search_range, SEEX, SEEY, vehicle::sm_pos, vehicle::tracking_on, type, omt_find_params::types, and tripoint::xy().

Referenced by start_game().

◆ pre_print_all_tile_info()

void game::pre_print_all_tile_info ( const tripoint lp,
const catacurses::window w_info,
int &  line,
int  last_line,
const visibility_variables cache 
)

Definition at line 6587 of file game.cpp.

6590{
6591 // get global area info according to look_around caret position
6592 // TODO: fix point types
6594 lp ) ) ) );
6595 // we only need the area name and then pass it to print_all_tile_info() function below
6596 const std::string area_name = cur_ter_m->get_name();
6597 print_all_tile_info( lp, w_info, area_name, 1, first_line, last_line, cache );
6598}
void print_all_tile_info(const tripoint &lp, const catacurses::window &w_look, const std::string &area_name, int column, int &line, int last_line, const visibility_variables &cache)
Definition: game.cpp:5762
point ms_to_omt_copy(point p)
coords::coord_point< tripoint, coords::origin::abs, coords::omt > tripoint_abs_omt
Definition: coordinates.h:493
std::string get_name() const
Definition: omdata.h:205

References oter_t::get_name(), map::getabs(), m, ms_to_omt_copy(), overmap_buffer, print_all_tile_info(), and overmapbuffer::ter().

Referenced by look_around().

◆ print_all_tile_info()

void game::print_all_tile_info ( const tripoint lp,
const catacurses::window w_look,
const std::string &  area_name,
int  column,
int &  line,
int  last_line,
const visibility_variables cache 
)

Definition at line 5762 of file game.cpp.

5767{
5768 visibility_type visibility = VIS_HIDDEN;
5769 const bool inbounds = m.inbounds( lp );
5770 if( inbounds ) {
5771 visibility = m.get_visibility( m.apparent_light_at( lp, cache ), cache );
5772 }
5773 const Creature *creature = critter_at( lp, true );
5774 switch( visibility ) {
5775 case VIS_CLEAR: {
5776 const optional_vpart_position vp = m.veh_at( lp );
5777 print_terrain_info( lp, w_look, area_name, column, line );
5778 print_fields_info( lp, w_look, column, line );
5779 print_trap_info( lp, w_look, column, line );
5780 print_creature_info( creature, w_look, column, line, last_line );
5781 print_vehicle_info( veh_pointer_or_null( vp ), vp ? vp->part_index() : -1, w_look, column, line,
5782 last_line );
5783 print_items_info( lp, w_look, column, line, last_line );
5784 print_graffiti_info( lp, w_look, column, line, last_line );
5785 }
5786 break;
5787 case VIS_BOOMER:
5788 case VIS_BOOMER_DARK:
5789 case VIS_DARK:
5790 case VIS_LIT:
5791 case VIS_HIDDEN:
5792 print_visibility_info( w_look, column, line, visibility );
5793
5794 if( creature != nullptr ) {
5795 std::vector<std::string> buf;
5796 if( u.sees_with_infrared( *creature ) ) {
5797 creature->describe_infrared( buf );
5798 } else if( u.sees_with_specials( *creature ) ) {
5799 creature->describe_specials( buf );
5800 }
5801 for( const std::string &s : buf ) {
5802 mvwprintw( w_look, point( 1, ++line ), s );
5803 }
5804 }
5805 break;
5806 }
5807 if( !inbounds ) {
5808 return;
5809 }
5810 auto this_sound = sounds::sound_at( lp );
5811 if( !this_sound.empty() ) {
5812 mvwprintw( w_look, point( 1, ++line ), _( "You heard %s from here." ), this_sound );
5813 } else {
5814 // Check other z-levels
5815 tripoint tmp = lp;
5816 for( tmp.z = -OVERMAP_DEPTH; tmp.z <= OVERMAP_HEIGHT; tmp.z++ ) {
5817 if( tmp.z == lp.z ) {
5818 continue;
5819 }
5820
5821 auto zlev_sound = sounds::sound_at( tmp );
5822 if( !zlev_sound.empty() ) {
5823 mvwprintw( w_look, point( 1, ++line ), tmp.z > lp.z ?
5824 _( "You heard %s from above." ) : _( "You heard %s from below." ), zlev_sound );
5825 }
5826 }
5827 }
5828}
bool sees_with_specials(const Creature &critter) const
Definition: character.cpp:6358
bool sees_with_infrared(const Creature &critter) const
Check whether the this player can see the other creature with infrared.
void print_fields_info(const tripoint &lp, const catacurses::window &w_look, int column, int &line)
Definition: game.cpp:5935
void print_terrain_info(const tripoint &lp, const catacurses::window &w_look, const std::string &area_name, int column, int &line)
Definition: game.cpp:5859
void print_graffiti_info(const tripoint &lp, const catacurses::window &w_look, int column, int &line, int last_line)
Definition: game.cpp:6029
void print_creature_info(const Creature *creature, const catacurses::window &w_look, int column, int &line, int last_line)
Definition: game.cpp:5973
void print_vehicle_info(const vehicle *veh, int veh_part, const catacurses::window &w_look, int column, int &line, int last_line)
Definition: game.cpp:5982
void print_items_info(const tripoint &lp, const catacurses::window &w_look, int column, int &line, int last_line)
Definition: game.cpp:5991
void print_visibility_info(const catacurses::window &w_look, int column, int &line, visibility_type visibility)
Definition: game.cpp:5830
void print_trap_info(const tripoint &lp, const catacurses::window &w_look, int column, int &line)
Definition: game.cpp:5953
void line(map *m, const ter_id &type, point p1, point p2)
Definition: mapgen.cpp:6290
std::string sound_at(const tripoint &location)
Definition: sounds.cpp:606

References _, map::apparent_light_at(), creature, critter_at(), map::get_visibility(), map::inbounds(), line(), m, catacurses::mvwprintw(), OVERMAP_DEPTH, OVERMAP_HEIGHT, print_creature_info(), print_fields_info(), print_graffiti_info(), print_items_info(), print_terrain_info(), print_trap_info(), print_vehicle_info(), print_visibility_info(), Character::sees_with_infrared(), Character::sees_with_specials(), sounds::sound_at(), u, map::veh_at(), veh_pointer_or_null(), VIS_BOOMER, VIS_BOOMER_DARK, VIS_CLEAR, VIS_DARK, VIS_HIDDEN, VIS_LIT, and tripoint::z.

Referenced by pre_print_all_tile_info().

◆ print_creature_info()

void game::print_creature_info ( const Creature creature,
const catacurses::window w_look,
int  column,
int &  line,
int  last_line 
)
private

Definition at line 5973 of file game.cpp.

5975{
5976 int vLines = last_line - line;
5977 if( creature != nullptr && ( u.sees( *creature ) || creature == &u ) ) {
5978 line = creature->print_info( w_look, ++line, vLines, column );
5979 }
5980}

References creature, line(), Character::sees(), and u.

Referenced by print_all_tile_info().

◆ print_fields_info()

void game::print_fields_info ( const tripoint lp,
const catacurses::window w_look,
int  column,
int &  line 
)
private

Definition at line 5935 of file game.cpp.

5937{
5938 const field &tmpfield = m.field_at( lp );
5939 for( auto &fld : tmpfield ) {
5940 const field_entry &cur = fld.second;
5941 if( fld.first.obj().has_fire && ( m.has_flag( TFLAG_FIRE_CONTAINER, lp ) ||
5942 m.ter( lp ) == t_pit_shallow || m.ter( lp ) == t_pit ) ) {
5943 const int max_width = getmaxx( w_look ) - column - 2;
5944 int lines = fold_and_print( w_look, point( column, ++line ), max_width, cur.color(),
5945 get_fire_fuel_string( lp ) ) - 1;
5946 line += lines;
5947 } else {
5948 mvwprintz( w_look, point( column, ++line ), cur.color(), cur.name() );
5949 }
5950 }
5951}
An active or passive effect existing on a tile.
Definition: field.h:20
nc_color color() const
Definition: field.cpp:94
std::string name() const
Definition: field.h:84
A variable sized collection of field entries on a given map square.
Definition: field.h:131
ter_id t_pit_shallow
Definition: mapdata.cpp:628
ter_id t_pit
Definition: mapdata.cpp:628

References field_entry::color(), map::field_at(), fold_and_print(), get_fire_fuel_string(), catacurses::getmaxx(), map::has_flag(), line(), m, mvwprintz(), field_entry::name(), t_pit, t_pit_shallow, map::ter(), and TFLAG_FIRE_CONTAINER.

Referenced by print_all_tile_info().

◆ print_graffiti_info()

void game::print_graffiti_info ( const tripoint lp,
const catacurses::window w_look,
int  column,
int &  line,
int  last_line 
)
private

Definition at line 6029 of file game.cpp.

6032{
6033 if( line > last_line ) {
6034 return;
6035 }
6036
6037 const int max_width = getmaxx( w_look ) - column - 2;
6038 if( m.has_graffiti_at( lp ) ) {
6039 fold_and_print( w_look, point( column, ++line ), max_width, c_light_gray,
6040 m.ter( lp ) == t_grave_new ? _( "Graffiti: %s" ) : _( "Inscription: %s" ),
6041 m.graffiti_at( lp ) );
6042 }
6043}
ter_id t_grave_new
Definition: mapdata.cpp:628

References _, c_light_gray, fold_and_print(), catacurses::getmaxx(), map::graffiti_at(), map::has_graffiti_at(), line(), m, t_grave_new, and map::ter().

Referenced by print_all_tile_info().

◆ print_items_info()

void game::print_items_info ( const tripoint lp,
const catacurses::window w_look,
int  column,
int &  line,
int  last_line 
)
private

Definition at line 5991 of file game.cpp.

5995{
5996 if( !m.sees_some_items( lp, u ) ) {
5997 return;
5998 } else if( m.has_flag( "CONTAINER", lp ) && !m.could_see_items( lp, u ) ) {
5999 mvwprintw( w_look, point( column, ++line ), _( "You cannot see what is inside of it." ) );
6000 } else if( u.has_effect( effect_blind ) || u.worn_with_flag( "BLIND" ) ) {
6001 mvwprintz( w_look, point( column, ++line ), c_yellow,
6002 _( "There's something there, but you can't see what it is." ) );
6003 return;
6004 } else {
6005 std::map<std::string, int> item_names;
6006 for( auto &item : m.i_at( lp ) ) {
6007 ++item_names[item.tname()];
6008 }
6009
6010 const int max_width = getmaxx( w_look ) - column - 1;
6011 for( auto it = item_names.begin(); it != item_names.end(); ++it ) {
6012 // last line but not last item
6013 if( line + 1 >= last_line && std::next( it ) != item_names.end() ) {
6014 mvwprintz( w_look, point( column, ++line ), c_yellow, _( "More items here…" ) );
6015 break;
6016 }
6017
6018 if( it->second > 1 ) {
6019 trim_and_print( w_look, point( column, ++line ), max_width, c_white,
6020 pgettext( "%s is the name of the item. %d is the quantity of that item.", "%s [%d]" ),
6021 it->first.c_str(), it->second );
6022 } else {
6023 trim_and_print( w_look, point( column, ++line ), max_width, c_white, it->first );
6024 }
6025 }
6026 }
6027}
bool could_see_items(const tripoint &p, const Creature &who) const
Check if the creature could see items at p if there were any items.
Definition: map.cpp:4867
static const efftype_id effect_blind("blind")

References _, c_white, c_yellow, map::could_see_items(), effect_blind, catacurses::getmaxx(), Creature::has_effect(), map::has_flag(), map::i_at(), line(), m, catacurses::mvwprintw(), mvwprintz(), pgettext(), map::sees_some_items(), item::tname(), trim_and_print(), u, and Character::worn_with_flag().

Referenced by print_all_tile_info().

◆ print_terrain_info()

void game::print_terrain_info ( const tripoint lp,
const catacurses::window w_look,
const std::string &  area_name,
int  column,
int &  line 
)
private

Definition at line 5859 of file game.cpp.

5862{
5863 const int max_width = getmaxx( w_look ) - column - 1;
5864 int lines;
5865
5866 const auto fmt_tile_info = []( const tripoint & lp ) {
5867 map &here = get_map();
5868 std::string ret;
5869 if( debug_mode ) {
5870 ret += lp.to_string();
5871 ret += "\n";
5872 }
5873 ret += here.tername( lp );
5875 ret += colorize( string_format( " [%s]", here.ter( lp )->id ), c_light_blue );
5876 }
5877 if( here.has_furn( lp ) ) {
5878 ret += string_format( "; %s", here.furnname( lp ) );
5880 ret += colorize( string_format( " [%s]", here.furn( lp )->id ), c_light_blue );
5881 }
5882 }
5883 return ret;
5884 };
5885
5886 std::string tile = string_format( "(%s) %s", area_name, fmt_tile_info( lp ) );
5887
5888 if( m.impassable( lp ) ) {
5889 lines = fold_and_print( w_look, point( column, line ), max_width, c_light_gray,
5890 _( "%s; Impassable" ),
5891 tile );
5892 } else {
5893 lines = fold_and_print( w_look, point( column, line ), max_width, c_light_gray,
5894 _( "%s; Movement cost %d" ),
5895 tile, m.move_cost( lp ) * 50 );
5896
5897 const auto ll = get_light_level( std::max( 1.0,
5898 LIGHT_AMBIENT_LIT - m.ambient_light_at( lp ) + 1.0 ) );
5899 mvwprintw( w_look, point( column, ++lines ), _( "Lighting: " ) );
5900 wprintz( w_look, ll.second, ll.first );
5901 }
5902
5903 std::string signage = m.get_signage( lp );
5904 if( !signage.empty() ) {
5905 trim_and_print( w_look, point( column, ++lines ), max_width, c_dark_gray,
5906 // NOLINTNEXTLINE(cata-text-style): the question mark does not end a sentence
5907 u.has_trait( trait_ILLITERATE ) ? _( "Sign: ???" ) : _( "Sign: %s" ), signage );
5908 }
5909
5910 if( m.has_zlevels() && lp.z > -OVERMAP_DEPTH && !m.has_floor( lp ) ) {
5911 // Print info about stuff below
5912 tripoint below( lp.xy(), lp.z - 1 );
5913 std::string tile_below = fmt_tile_info( below );
5914
5915 if( !m.has_floor_or_support( lp ) ) {
5916 fold_and_print( w_look, point( column, ++lines ), max_width, c_dark_gray,
5917 _( "Below: %s; No support" ),
5918 tile_below );
5919 } else {
5920 fold_and_print( w_look, point( column, ++lines ), max_width, c_dark_gray,
5921 _( "Below: %s; Walkable" ),
5922 tile_below );
5923 }
5924 }
5925
5926 int map_features = fold_and_print( w_look, point( column, ++lines ), max_width, c_dark_gray,
5927 m.features( lp ) );
5928 fold_and_print( w_look, point( column, ++lines ), max_width, c_light_gray, _( "Coverage: %d%%" ),
5929 m.coverage( lp ) );
5930 if( line < lines ) {
5931 line = lines + map_features - 1;
5932 }
5933}
bool has_floor_or_support(const tripoint &p) const
Definition: map.cpp:2121
float ambient_light_at(const tripoint &p) const
Definition: lightmap.cpp:682
std::string features(const tripoint &p)
Definition: map.cpp:1779
int coverage(const tripoint &p) const
Returns coverage value of the tile.
Definition: map.cpp:6384
int move_cost(const tripoint &p, const vehicle *ignored_vehicle=nullptr) const
Calculate the cost to move past the tile at p.
Definition: map.cpp:1845
static constexpr float LIGHT_AMBIENT_LIT
Definition: lightmap.h:18
std::pair< std::string, nc_color > get_light_level(const float light)
Definition: output.cpp:1621

References _, map::ambient_light_at(), c_dark_gray, c_light_blue, c_light_gray, colorize(), map::coverage(), debug_mode, display_object_ids, map::features(), fold_and_print(), get_light_level(), get_map, map::get_signage(), catacurses::getmaxx(), map::has_floor(), map::has_floor_or_support(), Character::has_trait(), map::has_zlevels(), anonymous_namespace{iexamine_elevator.cpp}::elevator::here(), map::impassable(), LIGHT_AMBIENT_LIT, line(), m, map::move_cost(), catacurses::mvwprintw(), OVERMAP_DEPTH, cata::hash64_detail::ret, string_format(), tripoint::to_string(), trait_ILLITERATE, trim_and_print(), u, wprintz(), tripoint::xy(), and tripoint::z.

Referenced by print_all_tile_info().

◆ print_trap_info()

void game::print_trap_info ( const tripoint lp,
const catacurses::window w_look,
int  column,
int &  line 
)
private

Definition at line 5953 of file game.cpp.

5956{
5957 const trap &tr = m.tr_at( lp );
5958 if( tr.can_see( lp, u ) ) {
5959 partial_con *pc = m.partial_con_at( lp );
5960 std::string tr_name;
5961 if( pc && tr.loadid == tr_unfinished_construction ) {
5962 const construction &built = pc->id.obj();
5963 tr_name = string_format( _( "Unfinished task: %s, %d%% complete" ), built.group->name(),
5964 pc->counter / 100000 );
5965 } else {
5966 tr_name = tr.name();
5967 }
5968
5969 mvwprintz( w_look, point( column, ++line ), tr.color, tr_name );
5970 }
5971}
partial_con * partial_con_at(const tripoint &p)
Definition: map.cpp:5274
static const trap_str_id tr_unfinished_construction("tr_unfinished_construction")
std::string name() const
construction_group_str_id group
Definition: construction.h:50
construction_id id
nc_color color
Definition: trap.h:93

References _, trap::can_see(), trap::color, partial_con::counter, construction::group, partial_con::id, line(), trap::loadid, m, mvwprintz(), construction_group::name(), trap::name(), int_id< T >::obj(), map::partial_con_at(), string_format(), map::tr_at(), tr_unfinished_construction, and u.

Referenced by print_all_tile_info().

◆ print_vehicle_info()

void game::print_vehicle_info ( const vehicle veh,
int  veh_part,
const catacurses::window w_look,
int  column,
int &  line,
int  last_line 
)
private

Definition at line 5982 of file game.cpp.

5984{
5985 if( veh ) {
5986 mvwprintw( w_look, point( column, ++line ), _( "There is a %s there. Parts:" ), veh->name );
5987 line = veh->print_part_list( w_look, ++line, last_line, getmaxx( w_look ), veh_part );
5988 }
5989}
int print_part_list(const catacurses::window &win, int y1, int max_y, int width, int p, int hl=-1, bool detail=false) const
Prints a list of all parts to the screen inside of a boxed window, possibly highlighting a selected o...

References _, catacurses::getmaxx(), line(), catacurses::mvwprintw(), vehicle::name, and vehicle::print_part_list().

Referenced by print_all_tile_info().

◆ print_visibility_info()

void game::print_visibility_info ( const catacurses::window w_look,
int  column,
int &  line,
visibility_type  visibility 
)
private

Definition at line 5830 of file game.cpp.

5832{
5833 const char *visibility_message = nullptr;
5834 switch( visibility ) {
5835 case VIS_CLEAR:
5836 visibility_message = _( "Clearly visible." );
5837 break;
5838 case VIS_BOOMER:
5839 visibility_message = _( "A bright pink blur." );
5840 break;
5841 case VIS_BOOMER_DARK:
5842 visibility_message = _( "A pink blur." );
5843 break;
5844 case VIS_DARK:
5845 visibility_message = _( "Darkness." );
5846 break;
5847 case VIS_LIT:
5848 visibility_message = _( "Bright light." );
5849 break;
5850 case VIS_HIDDEN:
5851 visibility_message = _( "Unseen." );
5852 break;
5853 }
5854
5855 mvwprintw( w_look, point( line, column ), visibility_message );
5856 line += 2;
5857}

References _, line(), catacurses::mvwprintw(), VIS_BOOMER, VIS_BOOMER_DARK, VIS_CLEAR, VIS_DARK, VIS_HIDDEN, and VIS_LIT.

Referenced by print_all_tile_info().

◆ process_activity()

void game::process_activity ( )
private

Definition at line 1651 of file game.cpp.

1652{
1653 if( !u.activity ) {
1654 return;
1655 }
1656
1657 while( u.moves > 0 && u.activity ) {
1658 u.activity.do_turn( u );
1659 }
1660}
void do_turn(player &p)
Performs the activity for a single turn.

References Character::activity, player_activity::do_turn(), Creature::moves, and u.

Referenced by do_turn().

◆ process_artifact()

void game::process_artifact ( item it,
player p 
)

Definition at line 11377 of file game.cpp.

11378{
11379 const bool worn = p.is_worn( it );
11380 const bool wielded = ( &it == &p.primary_weapon() );
11381 std::vector<art_effect_passive> effects = it.type->artifact->effects_carried;
11382 if( worn ) {
11383 const std::vector<art_effect_passive> &ew = it.type->artifact->effects_worn;
11384 effects.insert( effects.end(), ew.begin(), ew.end() );
11385 }
11386 if( wielded ) {
11387 const std::vector<art_effect_passive> &ew = it.type->artifact->effects_wielded;
11388 effects.insert( effects.end(), ew.begin(), ew.end() );
11389 }
11390
11391 if( it.is_tool() ) {
11392 // Recharge it if necessary
11393 if( it.ammo_remaining() < it.ammo_capacity() && calendar::once_every( 1_minutes ) ) {
11394 //Before incrementing charge, check that any extra requirements are met
11395 if( check_art_charge_req( it ) ) {
11396 switch( it.type->artifact->charge_type ) {
11397 case ARTC_NULL:
11398 case NUM_ARTCS:
11399 break; // dummy entries
11400 case ARTC_TIME:
11401 // Once per hour
11402 if( calendar::once_every( 1_hours ) ) {
11403 it.charges++;
11404 }
11405 break;
11406 case ARTC_SOLAR:
11407 if( calendar::once_every( 10_minutes ) &&
11408 is_in_sunlight( p.pos() ) ) {
11409 it.charges++;
11410 }
11411 break;
11412 // Artifacts can inflict pain even on Deadened folks.
11413 // Some weird Lovecraftian thing. ;P
11414 // (So DON'T route them through mod_pain!)
11415 case ARTC_PAIN:
11416 if( calendar::once_every( 1_minutes ) ) {
11417 add_msg( m_bad, _( "You suddenly feel sharp pain for no reason." ) );
11418 p.mod_pain_noresist( 3 * rng( 1, 3 ) );
11419 it.charges++;
11420 }
11421 break;
11422 case ARTC_HP:
11423 if( calendar::once_every( 1_minutes ) ) {
11424 add_msg( m_bad, _( "You feel your body decaying." ) );
11425 p.hurtall( 1, nullptr );
11426 it.charges++;
11427 }
11428 break;
11429 case ARTC_FATIGUE:
11430 if( calendar::once_every( 1_minutes ) ) {
11431 add_msg( m_bad, _( "You feel fatigue seeping into your body." ) );
11432 u.mod_fatigue( 3 * rng( 1, 3 ) );
11433 u.mod_stamina( -90 * rng( 1, 3 ) * rng( 1, 3 ) * rng( 2, 3 ) );
11434 it.charges++;
11435 }
11436 break;
11437 // Portals are energetic enough to charge the item.
11438 // Tears in reality are consumed too, but can't charge it.
11439 case ARTC_PORTAL:
11440 for( const tripoint &dest : m.points_in_radius( p.pos(), 1 ) ) {
11442 if( m.tr_at( dest ).loadid == tr_portal ) {
11443 add_msg( m_good, _( "The portal collapses!" ) );
11444 m.remove_trap( dest );
11445 it.charges++;
11446 break;
11447 }
11448 }
11449 break;
11450 }
11451 }
11452 }
11453 }
11454
11455 for( const art_effect_passive &i : effects ) {
11456 switch( i ) {
11457 case AEP_STR_UP:
11458 p.mod_str_bonus( +4 );
11459 break;
11460 case AEP_DEX_UP:
11461 p.mod_dex_bonus( +4 );
11462 break;
11463 case AEP_PER_UP:
11464 p.mod_per_bonus( +4 );
11465 break;
11466 case AEP_INT_UP:
11467 p.mod_int_bonus( +4 );
11468 break;
11469 case AEP_ALL_UP:
11470 p.mod_str_bonus( +2 );
11471 p.mod_dex_bonus( +2 );
11472 p.mod_per_bonus( +2 );
11473 p.mod_int_bonus( +2 );
11474 break;
11475 case AEP_SPEED_UP:
11476 // Handled in player::current_speed()
11477 break;
11478
11479 case AEP_PBLUE:
11480 if( p.get_rad() > 0 ) {
11481 p.mod_rad( -1 );
11482 }
11483 break;
11484
11485 case AEP_SMOKE:
11486 if( one_in( 10 ) ) {
11487 tripoint pt( p.posx() + rng( -1, 1 ),
11488 p.posy() + rng( -1, 1 ),
11489 p.posz() );
11490 m.add_field( pt, fd_smoke, rng( 1, 3 ) );
11491 }
11492 break;
11493
11494 case AEP_SNAKES:
11495 break; // Handled in player::hit()
11496
11497 case AEP_EXTINGUISH:
11498 for( const tripoint &dest : m.points_in_radius( p.pos(), 1 ) ) {
11499 m.mod_field_age( dest, fd_fire, -1_turns );
11500 }
11501 break;
11502
11503 case AEP_FUN:
11504 //Bonus fluctuates, wavering between 0 and 30-ish - usually around 12
11505 p.add_morale( MORALE_FEELING_GOOD, rng( 1, 2 ) * rng( 2, 3 ), 0, 3_turns, 0_turns, false );
11506 break;
11507
11508 case AEP_HUNGER:
11509 if( one_in( 100 ) ) {
11510 p.mod_stored_kcal( -10 );
11511 }
11512 break;
11513
11514 case AEP_THIRST:
11515 if( one_in( 120 ) ) {
11516 p.mod_thirst( 1 );
11517 }
11518 break;
11519
11520 case AEP_EVIL:
11521 if( one_in( 150 ) ) { // Once every 15 minutes, on average
11522 p.add_effect( effect_evil, 30_minutes );
11523 if( it.is_armor() ) {
11524 if( !worn ) {
11525 add_msg( _( "You have an urge to wear the %s." ),
11526 it.tname() );
11527 }
11528 } else if( !wielded ) {
11529 add_msg( _( "You have an urge to wield the %s." ),
11530 it.tname() );
11531 }
11532 }
11533 break;
11534
11535 case AEP_SCHIZO:
11536 break; // Handled in player::suffer()
11537
11538 case AEP_RADIOACTIVE:
11539 if( one_in( 4 ) ) {
11540 p.irradiate( 1.0f );
11541 }
11542 break;
11543
11544 case AEP_STR_DOWN:
11545 p.mod_str_bonus( -3 );
11546 break;
11547
11548 case AEP_DEX_DOWN:
11549 p.mod_dex_bonus( -3 );
11550 break;
11551
11552 case AEP_PER_DOWN:
11553 p.mod_per_bonus( -3 );
11554 break;
11555
11556 case AEP_INT_DOWN:
11557 p.mod_int_bonus( -3 );
11558 break;
11559
11560 case AEP_ALL_DOWN:
11561 p.mod_str_bonus( -2 );
11562 p.mod_dex_bonus( -2 );
11563 p.mod_per_bonus( -2 );
11564 p.mod_int_bonus( -2 );
11565 break;
11566
11567 case AEP_SPEED_DOWN:
11568 break; // Handled in player::current_speed()
11569
11570 default:
11571 //Suppress warnings
11572 break;
11573 }
11574 }
11575 // Recalculate, as it might have changed (by mod_*_bonus above)
11576 p.str_cur = p.get_str();
11577 p.int_cur = p.get_int();
11578 p.dex_cur = p.get_dex();
11579 p.per_cur = p.get_per();
11580}
@ ARTC_PORTAL
Definition: artifact.h:69
@ ARTC_FATIGUE
Definition: artifact.h:68
@ ARTC_NULL
Definition: artifact.h:63
@ ARTC_SOLAR
Definition: artifact.h:65
@ NUM_ARTCS
Definition: artifact.h:70
@ ARTC_HP
Definition: artifact.h:67
@ ARTC_TIME
Definition: artifact.h:64
@ ARTC_PAIN
Definition: artifact.h:66
virtual void mod_per_bonus(int nper)
Definition: character.cpp:4209
virtual void mod_dex_bonus(int ndex)
Definition: character.cpp:4204
int str_cur
Definition: character.h:264
void mod_rad(int mod)
Definition: character.cpp:7079
virtual int get_dex() const
Definition: character.cpp:4093
virtual void mod_stored_kcal(int nkcal)
Modifiers for need values exclusive to characters.
Definition: character.cpp:4324
bool is_worn(const item &thing) const
Definition: character.h:1099
virtual int get_int() const
Definition: character.cpp:4101
virtual void mod_fatigue(int nfatigue)
Definition: character.cpp:4455
virtual void mod_str_bonus(int nstr)
Definition: character.cpp:4199
int int_cur
Definition: character.h:266
int get_rad() const
Definition: character.cpp:7069
void add_morale(const morale_type &type, int bonus, int max_bonus=0, const time_duration &duration=1_hours, const time_duration &decay_start=30_minutes, bool capped=false, const itype *item_type=nullptr)
Definition: character.cpp:9094
virtual int get_per() const
Definition: character.cpp:4097
void hurtall(int dam, Creature *source, bool disturb=true)
Hurts all body parts for dam, no armor reduction.
Definition: character.cpp:8664
bool irradiate(float rads, bool bypass=false)
Handles mitigation and application of radiation.
Definition: suffer.cpp:1601
virtual void mod_int_bonus(int nint)
Definition: character.cpp:4214
virtual void mod_pain_noresist(int npain)
Definition: creature.cpp:1393
bool is_in_sunlight(const tripoint &p)
Returns true if p is outdoors and it is sunny.
Definition: game.cpp:4855
bool is_tool() const
Definition: item.cpp:6984
int charges
Definition: item.h:2209
bool is_armor() const
Definition: item.cpp:6730
bool add_field(const tripoint &p, const field_type_id &type_id, int intensity=INT_MAX, const time_duration &age=0_turns, bool hit_player=true)
Add field entry at point, or set intensity if present.
Definition: map.cpp:5536
time_duration mod_field_age(const tripoint &p, const field_type_id &type, const time_duration &offset)
Increment/decrement age of field entry at point.
Definition: map.cpp:5449
void remove_trap(const tripoint &p)
Definition: map.cpp:5394
art_effect_passive
Definition: enums.h:99
@ AEP_EXTINGUISH
Definition: enums.h:114
field_type_id fd_smoke
Definition: field_type.cpp:346
field_type_id fd_fatigue
Definition: field_type.cpp:354
static const efftype_id effect_evil("evil")
static const trap_str_id tr_portal("tr_portal")
const morale_type MORALE_FEELING_GOOD("morale_feeling_good")

References _, Creature::add_effect(), map::add_field(), Character::add_morale(), add_msg(), AEP_ALL_DOWN, AEP_ALL_UP, AEP_DEX_DOWN, AEP_DEX_UP, AEP_EVIL, AEP_EXTINGUISH, AEP_FUN, AEP_HUNGER, AEP_INT_DOWN, AEP_INT_UP, AEP_PBLUE, AEP_PER_DOWN, AEP_PER_UP, AEP_RADIOACTIVE, AEP_SCHIZO, AEP_SMOKE, AEP_SNAKES, AEP_SPEED_DOWN, AEP_SPEED_UP, AEP_STR_DOWN, AEP_STR_UP, AEP_THIRST, item::ammo_capacity(), item::ammo_remaining(), ARTC_FATIGUE, ARTC_HP, ARTC_NULL, ARTC_PAIN, ARTC_PORTAL, ARTC_SOLAR, ARTC_TIME, itype::artifact, item::charges, check_art_charge_req(), anonymous_namespace{iexamine_elevator.cpp}::elevator::dest(), Character::dex_cur, effect_evil, fd_fatigue, fd_fire, fd_smoke, Character::get_dex(), Character::get_int(), Character::get_per(), Character::get_rad(), Character::get_str(), Character::hurtall(), Character::int_cur, Character::irradiate(), item::is_armor(), is_in_sunlight(), item::is_tool(), Character::is_worn(), trap::loadid, m, m_bad, m_good, Character::mod_dex_bonus(), Character::mod_fatigue(), map::mod_field_age(), Character::mod_int_bonus(), Creature::mod_pain_noresist(), Character::mod_per_bonus(), Character::mod_rad(), Character::mod_stamina(), Character::mod_stored_kcal(), Character::mod_str_bonus(), Character::mod_thirst(), MORALE_FEELING_GOOD, NUM_ARTCS, calendar::once_every(), one_in(), Character::per_cur, map::points_in_radius(), Character::pos(), Character::posx(), Character::posy(), Character::posz(), Character::primary_weapon(), map::remove_field(), map::remove_trap(), rng(), Character::str_cur, item::tname(), map::tr_at(), tr_portal, item::type, and u.

◆ process_voluntary_act_interrupt()

void game::process_voluntary_act_interrupt ( )
private

Definition at line 1611 of file game.cpp.

1612{
1613 if( u.has_effect( effect_sleep ) ) {
1614 // Can't interrupt
1615 return;
1616 }
1617
1618 bool has_activity = u.activity && u.activity.moves_left > 0;
1619 bool is_travelling = u.has_destination() && !u.omt_path.empty();
1620
1621 if( !has_activity && !is_travelling ) {
1622 // Nohing to interrupt
1623 return;
1624 }
1625
1626 // Key poll may be quite expensive, so limit it to 10 times per second.
1627 static auto last_poll = std::chrono::steady_clock::now();
1628 auto now = std::chrono::steady_clock::now();
1629 int64_t difference = std::chrono::duration_cast<std::chrono::milliseconds>
1630 ( now - last_poll ).count();
1631
1632 if( difference > 100 ) {
1634 last_poll = now;
1635 }
1636
1637 // If player is performing a task and a monster is dangerously close, warn them
1638 // regardless of previous safemode warnings.
1639 // Distraction Manager can change this.
1640 if( ( has_activity || is_travelling ) && !u.has_activity( activity_id( "ACT_AIM" ) ) &&
1642 Creature *hostile_critter = is_hostile_very_close();
1643 if( hostile_critter != nullptr ) {
1645 string_format( _( "The %s is dangerously close!" ),
1646 hostile_critter->get_name() ) );
1647 }
1648 }
1649}
bool has_activity(const activity_id &type) const
Check if player currently has a given activity.
Definition: character.cpp:9225
virtual std::string get_name() const =0
void handle_key_blocking_activity()
Definition: game.cpp:1972
int moves_left
The number of moves remaining in this activity before it is complete.

References _, Character::activity, cancel_activity_or_ignore_query(), effect_sleep, Creature::get_name(), handle_key_blocking_activity(), Character::has_activity(), Character::has_destination(), Creature::has_effect(), hostile_spotted_near, player_activity::is_distraction_ignored(), is_hostile_very_close(), player_activity::moves_left, Character::omt_path, string_format(), and u.

Referenced by do_turn().

◆ prompt_dangerous_tile()

bool game::prompt_dangerous_tile ( const tripoint dest_loc) const

Definition at line 8725 of file game.cpp.

8726{
8727 static const iexamine_function ledge_examine = iexamine_function_from_string( "ledge" );
8728 std::vector<std::string> harmful_stuff = get_dangerous_tile( dest_loc );
8729
8730 if( harmful_stuff.empty() ) {
8731 return true;
8732 }
8733
8734 if( !( harmful_stuff.size() == 1 && m.tr_at( dest_loc ).loadid == tr_ledge ) ) {
8735 return query_yn( _( "Really step into %s?" ), enumerate_as_string( harmful_stuff ) ) ;
8736 }
8737
8738 if( !u.is_mounted() ) {
8739 ledge_examine( u, dest_loc );
8740 return false;
8741 }
8742
8743 add_msg( m_warning, _( "Your %s refuses to move over that ledge!" ),
8744 u.mounted_creature->get_name() );
8745 return false;
8746}
iexamine_function iexamine_function_from_string(const std::string &function_name)
Given then name of one of the above functions, returns the matching function pointer.
Definition: iexamine.cpp:6213
void(*)(player &, const tripoint &) iexamine_function
Definition: iexamine.h:142

References _, add_msg(), enumerate_as_string(), get_dangerous_tile(), iexamine_function_from_string(), Character::is_mounted(), trap::loadid, m, m_warning, Character::mounted_creature, query_yn(), map::tr_at(), tr_ledge, and u.

Referenced by npc_menu(), and walk_move().

◆ quickload()

void game::quickload ( )
private

Definition at line 11345 of file game.cpp.

11346{
11347 const WORLDPTR active_world = world_generator->active_world;
11348 if( active_world == nullptr ) {
11349 return;
11350 }
11351
11352 if( active_world->save_exists( save_t::from_save_id( u.get_save_id() ) ) ) {
11353 if( moves_since_last_save != 0 ) { // See if we need to reload anything
11354 MAPBUFFER.clear();
11356 try {
11357 setup();
11358 } catch( const std::exception &err ) {
11359 debugmsg( "Error: %s", err.what() );
11360 }
11362 }
11363 } else {
11364 popup_getkey( _( "No saves for current character yet." ) );
11365 }
11366}
bool load(const std::string &world)
Attempt to load first valid save (if any) in world.
Definition: game.cpp:2517
void setup()
Definition: game.cpp:479
static save_t from_save_id(const std::string &save_id)
int popup_getkey(const char *const mes, Args &&... args)
Definition: output.h:457
bool save_exists(const save_t &name) const

References _, mapbuffer::clear(), overmapbuffer::clear(), debugmsg, save_t::from_save_id(), avatar::get_save_id(), load(), MAPBUFFER, moves_since_last_save, overmap_buffer, popup_getkey(), WORLD::save_exists(), setup(), u, and world_generator.

Referenced by handle_action().

◆ quicksave()

void game::quicksave ( )

Definition at line 11323 of file game.cpp.

11324{
11325 //Don't autosave if the player hasn't done anything since the last autosave/quicksave,
11326 if( !moves_since_last_save ) {
11327 return;
11328 }
11329 add_msg( m_info, _( "Saving game, this may take a while" ) );
11330
11332 popup.message( "%s", _( "Saving game, this may take a while" ) );
11335
11336 time_t now = time( nullptr ); //timestamp for start of saving procedure
11337
11338 //perform save
11339 save();
11340 //Now reset counters for autosaving, so we don't immediately autosave after a quicksave or autosave.
11342 last_save_timestamp = now;
11343}

References _, add_msg(), last_save_timestamp, m_info, moves_since_last_save, popup(), ui_manager::redraw(), refresh_display(), save(), and time.

Referenced by autosave(), and handle_action().

◆ reenter_fullscreen()

void game::reenter_fullscreen ( )

Definition at line 467 of file game.cpp.

468{
469 if( was_fullscreen ) {
470 if( !fullscreen ) {
472 }
473 }
474}

References fullscreen, toggle_fullscreen(), and was_fullscreen.

Referenced by list_items_monsters(), and look_around().

◆ reload_npcs()

void game::reload_npcs ( )

Unloads, then loads the NPCs.

Definition at line 880 of file game.cpp.

881{
882 // TODO: Make it not invoke the "on_unload" command for the NPCs that will be loaded anyway
883 // and not invoke "on_load" for those NPCs that avoided unloading this way.
884 unload_npcs();
885 load_npcs();
886}

References load_npcs(), and unload_npcs().

Referenced by load(), overmap_npc_move(), vertical_move(), and vertical_shift().

◆ reload_tileset()

void game::reload_tileset ( std::function< void(std::string)>  out)

Definition at line 431 of file game.cpp.

432{
433#if defined(TILES)
434 // Disable UIs below to avoid accessing the tile context during loading.
436 try {
437 tilecontext->reinit();
438 std::vector<mod_id> dummy;
439 tilecontext->load_tileset(
440 get_option<std::string>( "TILES" ),
441 world_generator->active_world ? world_generator->active_world->active_mod_order : dummy,
442 /*precheck=*/false,
443 /*force=*/true,
444 /*pump_events=*/true
445 );
446 tilecontext->do_tile_loading_report( out );
447 } catch( const std::exception &err ) {
448 popup( _( "Loading the tileset failed: %s" ), err.what() );
449 }
450 g->reset_zoom();
451 g->mark_main_ui_adaptor_resize();
452#endif // TILES
453}

References _, g, popup(), and world_generator.

Referenced by handle_action().

◆ remoteveh()

vehicle * game::remoteveh ( )

Returns the current remotely controlled vehicle.

Definition at line 2251 of file game.cpp.

2252{
2254 return remoteveh_cache;
2255 }
2257 std::stringstream remote_veh_string( u.get_value( "remote_controlling_vehicle" ) );
2258 if( remote_veh_string.str().empty() ||
2260 remoteveh_cache = nullptr;
2261 } else {
2262 tripoint vp;
2263 remote_veh_string >> vp.x >> vp.y >> vp.z;
2264 vehicle *veh = veh_pointer_or_null( m.veh_at( vp ) );
2265 if( veh && veh->fuel_left( itype_battery, true ) > 0 ) {
2266 remoteveh_cache = veh;
2267 } else {
2268 remoteveh_cache = nullptr;
2269 }
2270 }
2271 return remoteveh_cache;
2272}
vehicle * remoteveh_cache
Definition: game.h:1044
int fuel_left(const itype_id &ftype, bool recurse=false) const
Definition: vehicle.cpp:3361
static const bionic_id bio_remote("bio_remote")
static const itype_id itype_remotevehcontrol("remotevehcontrol")
static const itype_id itype_battery("battery")

References bio_remote, vehicle::fuel_left(), Creature::get_value(), Character::has_active_bionic(), Character::has_active_item(), itype_battery, itype_remotevehcontrol, m, remoteveh_cache, remoteveh_cache_time, calendar::turn, u, map::veh_at(), veh_pointer_or_null(), tripoint::x, tripoint::y, and tripoint::z.

Referenced by control_vehicle(), and handle_action().

◆ remove_npc_follower()

void game::remove_npc_follower ( const character_id id)

Remove follower id from follower set.

Definition at line 1881 of file game.cpp.

1882{
1883 follower_ids.erase( id );
1884 u.follower_ids.erase( id );
1885}

References follower_ids, player::follower_ids, and u.

Referenced by cleanup_dead().

◆ remove_zombie()

void game::remove_zombie ( const monster critter)

Definition at line 4735 of file game.cpp.

4736{
4737 critter_tracker->remove( critter );
4738}

References critter_tracker.

Referenced by despawn_monster(), disable_robot(), start_game(), and vertical_move().

◆ replace_stair_monsters()

void game::replace_stair_monsters ( )
private

Definition at line 10829 of file game.cpp.

10830{
10831 for( auto &elem : coming_to_stairs ) {
10832 elem.staircount = 0;
10833 const tripoint pnt( elem.pos().xy(), get_levz() );
10834 place_critter_around( make_shared_fast<monster>( elem ), pnt, 10 );
10835 }
10836
10837 coming_to_stairs.clear();
10838}
std::vector< monster > coming_to_stairs
Definition: game.h:982

References coming_to_stairs, get_levz(), and place_critter_around().

◆ reset_item_list_state()

void game::reset_item_list_state ( const catacurses::window window,
int  height,
bool  bRadiusSort 
)
private

Definition at line 7184 of file game.cpp.

7186{
7187 const int width = getmaxx( window );
7188 for( int i = 1; i < TERMX; i++ ) {
7189 if( i < width ) {
7190 mvwputch( window, point( i, 0 ), c_light_gray, LINE_OXOX ); // -
7191 mvwputch( window, point( i, TERMY - height - 1 ), c_light_gray,
7192 LINE_OXOX ); // -
7193 }
7194
7195 if( i < TERMY - height ) {
7196 mvwputch( window, point( 0, i ), c_light_gray, LINE_XOXO ); // |
7197 mvwputch( window, point( width - 1, i ), c_light_gray, LINE_XOXO ); // |
7198 }
7199 }
7200
7201 mvwputch( window, point_zero, c_light_gray, LINE_OXXO ); // |^
7202 mvwputch( window, point( width - 1, 0 ), c_light_gray, LINE_OOXX ); // ^|
7203
7204 mvwputch( window, point( 0, TERMY - height - 1 ), c_light_gray,
7205 LINE_XXXO ); // |-
7206 mvwputch( window, point( width - 1, TERMY - height - 1 ), c_light_gray,
7207 LINE_XOXX ); // -|
7208
7209 mvwprintz( window, point( 2, 0 ), c_light_green, "<Tab> " );
7210 wprintz( window, c_white, _( "Items" ) );
7211
7212 std::string sSort;
7213 if( bRadiusSort ) {
7214 //~ Sort type: distance.
7215 sSort = _( "<s>ort: dist" );
7216 } else {
7217 //~ Sort type: category.
7218 sSort = _( "<s>ort: cat" );
7219 }
7220
7221 int letters = utf8_width( sSort );
7222
7223 shortcut_print( window, point( getmaxx( window ) - letters, 0 ), c_white, c_light_green, sSort );
7224
7225 std::vector<std::string> tokens;
7226 if( !sFilter.empty() ) {
7227 tokens.emplace_back( _( "<R>eset" ) );
7228 }
7229
7230 tokens.emplace_back( _( "<E>xamine" ) );
7231 tokens.emplace_back( _( "<C>ompare" ) );
7232 tokens.emplace_back( _( "<F>ilter" ) );
7233 tokens.emplace_back( _( "<+/->Priority" ) );
7234
7235 int gaps = tokens.size() + 1;
7236 letters = 0;
7237 int n = tokens.size();
7238 for( int i = 0; i < n; i++ ) {
7239 letters += utf8_width( tokens[i] ) - 2; //length ignores < >
7240 }
7241
7242 int usedwidth = letters;
7243 const int gap_spaces = ( width - usedwidth ) / gaps;
7244 usedwidth += gap_spaces * gaps;
7245 point pos( gap_spaces + ( width - usedwidth ) / 2, TERMY - height - 1 );
7246
7247 for( int i = 0; i < n; i++ ) {
7248 pos.x += shortcut_print( window, pos, c_white, c_light_green,
7249 tokens[i] ) + gap_spaces;
7250 }
7251}
#define LINE_OOXX
Definition: output.h:43
#define LINE_OXXO
Definition: output.h:42

References _, c_light_gray, c_light_green, c_white, catacurses::getmaxx(), LINE_OOXX, LINE_OXOX, LINE_OXXO, LINE_XOXO, LINE_XOXX, LINE_XXXO, mvwprintz(), mvwputch(), point_zero, sFilter, shortcut_print(), TERMX, TERMY, utf8_width(), wprintz(), and point::x.

Referenced by list_items().

◆ reset_light_level()

void game::reset_light_level ( )

Definition at line 3574 of file game.cpp.

3575{
3576 for( float &lev : latest_lightlevels ) {
3577 lev = -std::numeric_limits<float>::max();
3578 }
3579}

References latest_lightlevels.

Referenced by do_turn(), and game().

◆ reset_npc_dispositions()

void game::reset_npc_dispositions ( )
private

Definition at line 2633 of file game.cpp.

2634{
2635 for( auto elem : follower_ids ) {
2636 shared_ptr_fast<npc> npc_to_get = overmap_buffer.find_npc( elem );
2637 if( !npc_to_get ) {
2638 continue;
2639 }
2640 npc *npc_to_add = npc_to_get.get();
2641 npc_to_add->chatbin.missions.clear();
2642 npc_to_add->chatbin.missions_assigned.clear();
2643 npc_to_add->mission = NPC_MISSION_NULL;
2644 npc_to_add->chatbin.mission_selected = nullptr;
2645 npc_to_add->set_attitude( NPCATT_NULL );
2646 npc_to_add->op_of_u.anger = 0;
2647 npc_to_add->op_of_u.fear = 0;
2648 npc_to_add->op_of_u.trust = 0;
2649 npc_to_add->op_of_u.value = 0;
2650 npc_to_add->op_of_u.owed = 0;
2651 npc_to_add->set_fac( faction_id( "no_faction" ) );
2653 npc_to_add->global_omt_location(),
2654 npc_to_add->getID() ) );
2655
2656 }
2657
2658}
void set_attitude(npc_attitude new_attitude)
Definition: npc.cpp:3169
npc_chatbin chatbin
Definition: npc.h:1294
void add_new_mission(mission *miss)
See npc_chatbin::add_new_mission.
Definition: npc.cpp:2663
npc_opinion op_of_u
Definition: npc.h:1293
void set_fac(const faction_id &id)
Definition: npc.cpp:479
std::vector< mission * > missions_assigned
Mission that have been assigned by this NPC to a player character.
Definition: npc.h:715
mission * mission_selected
The mission (if any) that we talk about right now.
Definition: npc.h:720
std::vector< mission * > missions
Missions that the NPC can give out.
Definition: npc.h:711
int value
Definition: npc.h:205
int trust
Definition: npc.h:203
int owed
Definition: npc.h:207
int fear
Definition: npc.h:204
int anger
Definition: npc.h:206

References npc::add_new_mission(), npc_opinion::anger, npc::chatbin, npc_opinion::fear, overmapbuffer::find_npc(), follower_ids, Character::getID(), Character::global_omt_location(), npc::mission, npc_chatbin::mission_selected, npc_chatbin::missions, npc_chatbin::missions_assigned, NPC_MISSION_NULL, NPCATT_NULL, npc::op_of_u, ORIGIN_ANY_NPC, overmap_buffer, npc_opinion::owed, mission::reserve_random(), npc::set_attitude(), npc::set_fac(), npc_opinion::trust, and npc_opinion::value.

Referenced by cleanup_at_end().

◆ reset_zoom()

void game::reset_zoom ( )

Definition at line 7099 of file game.cpp.

7100{
7101#if defined(TILES)
7103 rescale_tileset( tileset_zoom );
7104#endif // TILES
7105}

References DEFAULT_TILESET_ZOOM, and tileset_zoom.

◆ revive_corpse()

bool game::revive_corpse ( const tripoint p,
item it 
)

Revives a corpse at given location.

The monster type and some of its properties are deducted from the corpse. If reviving succeeds, the location is guaranteed to have a new monster there (see critter_at).

Parameters
pThe place where to put the revived monster.
itThe corpse item, it must be a valid corpse (see item::is_corpse).
Returns
Whether the corpse has actually been redivided. Reviving may fail for many reasons, including no space to put the monster, corpse being to much damaged etc. If the monster was revived, the caller should remove the corpse item. If reviving failed, the item is unchanged, as is the environment (no new monsters).

Definition at line 4865 of file game.cpp.

4866{
4867 if( !it.is_corpse() ) {
4868 debugmsg( "Tried to revive a non-corpse." );
4869 return false;
4870 }
4871 shared_ptr_fast<monster> newmon_ptr = make_shared_fast<monster>
4872 ( it.get_mtype()->id );
4873 monster &critter = *newmon_ptr;
4874 critter.init_from_item( it );
4875 if( critter.get_hp() < 1 ) {
4876 // Failed reanimation due to corpse being too burned
4877 return false;
4878 }
4879 if( it.has_flag( "FIELD_DRESS" ) || it.has_flag( "FIELD_DRESS_FAILED" ) ||
4880 it.has_flag( "QUARTERED" ) ) {
4881 // Failed reanimation due to corpse being butchered
4882 return false;
4883 }
4884
4885 critter.no_extra_death_drops = true;
4886 critter.add_effect( effect_downed, 5_turns, num_bp );
4887 for( const item &component : it.components ) {
4888 critter.corpse_components.push_back( component );
4889 }
4890
4891 if( it.get_var( "zlave" ) == "zlave" ) {
4892 critter.add_effect( effect_pacified, 1_turns, num_bp );
4893 critter.add_effect( effect_pet, 1_turns, num_bp );
4894 }
4895
4896 if( it.get_var( "no_ammo" ) == "no_ammo" ) {
4897 for( auto &ammo : critter.ammo ) {
4898 ammo.second = 0;
4899 }
4900 }
4901
4902 return place_critter_at( newmon_ptr, p );
4903}
monster * place_critter_at(const mtype_id &id, const tripoint &p)
Adds critters to the reality bubble, creating them if necessary.
Definition: game.cpp:4663
double get_var(const std::string &name, double default_value) const
Definition: item.cpp:1034
const mtype * get_mtype() const
Definition: item.cpp:6651
std::list< item > components
Definition: item.h:2172
bool has_flag(const std::string &flag) const
Definition: item.cpp:5329
bool is_corpse() const
Whether this is a corpse item.
Definition: item.cpp:6646
int get_hp(const bodypart_id &) const override
Definition: monster.cpp:2955
bool no_extra_death_drops
Definition: monster.h:480
std::vector< item > corpse_components
Definition: monster.h:457
void init_from_item(const item &itm)
Initialize values like speed / hp from data of an item.
Definition: monster.cpp:2825
static const efftype_id effect_downed("downed")
static const efftype_id effect_pacified("pacified")

References monster::add_effect(), monster::ammo, item::components, monster::corpse_components, debugmsg, effect_downed, effect_pacified, effect_pet, monster::get_hp(), item::get_mtype(), item::get_var(), item::has_flag(), mtype::id, monster::init_from_item(), item::is_corpse(), monster::no_extra_death_drops, num_bp, and place_critter_at().

◆ save()

bool game::save ( )

Returns false if saving failed.

Definition at line 2747 of file game.cpp.

2748{
2750 try {
2751 if( !save_player_data() ||
2753 !save_artifacts() ||
2754 !save_maps() ||
2755 !get_auto_pickup().save_character() ||
2757 !get_safemode().save_character() ||
2758 !cata::save_world_lua_state( g->get_world_base_save_path() + "/lua_state.json" ) ||
2759 !save_uistate_data( *this )
2760 ) {
2761 return false;
2762 } else {
2763 world_generator->last_world_name = world_generator->active_world->world_name;
2764 world_generator->last_character_name = u.name;
2765 world_generator->save_last_world_info();
2766 world_generator->active_world->add_save( save_t::from_save_id( u.get_save_id() ) );
2767 return true;
2768 }
2769 } catch( std::ios::failure &err ) {
2770 popup( _( "Failed to save game data" ) );
2771 return false;
2772 }
2773}
bool save_player_data()
Definition: game.cpp:2688
static bool save_uistate_data(const game &g)
Definition: game.cpp:2739
@ failure
Definition: behavior.h:20
bool save_world_lua_state(const std::string &)
Definition: catalua.cpp:64
void run_on_game_save_hooks(lua_state &state)
Definition: catalua.cpp:415

References _, behavior::failure, save_t::from_save_id(), g, get_auto_notes_settings(), get_auto_pickup(), DynamicDataLoader::get_instance(), get_safemode(), avatar::get_save_id(), Character::name, popup(), cata::run_on_game_save_hooks(), save(), save_artifacts(), save_factions_missions_npcs(), save_maps(), save_player_data(), save_uistate_data(), cata::save_world_lua_state(), u, and world_generator.

Referenced by handle_action(), quicksave(), and save().

◆ save_artifacts()

bool game::save_artifacts ( )
private

Definition at line 2669 of file game.cpp.

2670{
2671 std::string artfilename = get_world_base_save_path() + "/" + SAVE_ARTIFACTS;
2672 return ::save_artifacts( artfilename );
2673}
bool save_artifacts(const std::string &path)
Definition: artifact.cpp:1277
static const std::string SAVE_ARTIFACTS("artifacts.gsav")

References get_world_base_save_path(), SAVE_ARTIFACTS(), and save_artifacts().

Referenced by cleanup_at_end(), and save().

◆ save_cyborg()

void game::save_cyborg ( item cyborg,
const tripoint couch_pos,
player installer 
)

Turns Broken Cyborg monster into Cyborg NPC via surgery.

Definition at line 4926 of file game.cpp.

4927{
4928 int assist_bonus = installer.get_effect_int( effect_assisted );
4929
4930 float adjusted_skill = installer.bionics_adjusted_skill( skill_firstaid,
4933 -1 );
4934
4935 int damage = cyborg->damage();
4936 int dmg_lvl = cyborg->damage_level( 4 );
4937 int difficulty = 12;
4938
4939 if( damage != 0 ) {
4940
4941 popup( _( "WARNING: Patient's body is damaged. Difficulty of the procedure is increased by %s." ),
4942 dmg_lvl );
4943
4944 // Damage of the cyborg increases difficulty
4945 difficulty += dmg_lvl;
4946 }
4947
4948 int chance_of_success = bionic_manip_cos( adjusted_skill + assist_bonus, difficulty );
4949 int success = chance_of_success - rng( 1, 100 );
4950
4951 if( !g->u.query_yn(
4952 _( "WARNING: %i percent chance of SEVERE damage to all body parts! Continue anyway?" ),
4953 100 - static_cast<int>( chance_of_success ) ) ) {
4954 return;
4955 }
4956
4957 if( success > 0 ) {
4958 add_msg( m_good, _( "Successfully removed Personality override." ) );
4959 add_msg( m_bad, _( "Autodoc immediately destroys the CBM upon removal." ) );
4960
4961 delete_cyborg_item( g->m, couch_pos, cyborg );
4962
4963 const string_id<npc_template> npc_cyborg( "cyborg_rescued" );
4964 shared_ptr_fast<npc> tmp = make_shared_fast<npc>();
4965 tmp->load_npc_template( npc_cyborg );
4966 tmp->spawn_at_precise( { get_levx(), get_levy() }, couch_pos );
4968 tmp->hurtall( dmg_lvl * 10, nullptr );
4969 tmp->add_effect( effect_downed, rng( 1_turns, 4_turns ), num_bp, 0, true );
4970 load_npcs();
4971
4972 } else {
4973 const int failure_level = static_cast<int>( std::sqrt( std::abs( success ) * 4.0 * difficulty /
4974 adjusted_skill ) );
4975 const int fail_type = std::min( 5, failure_level );
4976 switch( fail_type ) {
4977 case 1:
4978 case 2:
4979 add_msg( m_info, _( "The removal fails." ) );
4980 add_msg( m_bad, _( "The body is damaged." ) );
4981 cyborg->set_damage( damage + 1000 );
4982 break;
4983 case 3:
4984 case 4:
4985 add_msg( m_info, _( "The removal fails badly." ) );
4986 add_msg( m_bad, _( "The body is badly damaged!" ) );
4987 cyborg->set_damage( damage + 2000 );
4988 break;
4989 case 5:
4990 add_msg( m_info, _( "The removal is a catastrophe." ) );
4991 add_msg( m_bad, _( "The body is destroyed!" ) );
4992 delete_cyborg_item( g->m, couch_pos, cyborg );
4993 break;
4994 default:
4995 break;
4996 }
4997
4998 }
4999
5000}
int bionic_manip_cos(float adjusted_skill, int bionic_difficulty)
Definition: bionics.cpp:1965
float bionics_adjusted_skill(const skill_id &most_important_skill, const skill_id &important_skill, const skill_id &least_important_skill, int skill_level=-1)
Calculate skill for (un)installing bionics.
Definition: bionics.cpp:1922
item & set_damage(int qty)
Filter setting damage constrained by min_damage and max_damage.
Definition: item.cpp:718
int damage_level(int max) const
Scale item damage to the given number of levels.
Definition: item.cpp:705
int damage() const
How much damage has the item sustained?
Definition: item.cpp:700
static const skill_id skill_computer("computer")
static void delete_cyborg_item(map &m, const tripoint &couch_pos, item *cyborg)
Definition: game.cpp:4905
static const efftype_id effect_assisted("assisted")
static const skill_id skill_electronics("electronics")
@ success
Definition: behavior.h:20

References _, add_msg(), bionic_manip_cos(), Character::bionics_adjusted_skill(), item::damage(), item::damage_level(), delete_cyborg_item(), effect_assisted, effect_downed, g, Creature::get_effect_int(), get_levx(), get_levy(), overmapbuffer::insert_npc(), load_npcs(), m_bad, m_good, m_info, num_bp, overmap_buffer, popup(), rng(), item::set_damage(), skill_computer, skill_electronics, skill_firstaid, and behavior::success.

◆ save_factions_missions_npcs()

bool game::save_factions_missions_npcs ( )
private

Definition at line 2661 of file game.cpp.

2662{
2663 std::string masterfile = get_world_base_save_path() + "/" + SAVE_MASTER;
2664 return write_to_file( masterfile, [&]( std::ostream & fout ) {
2665 serialize_master( fout );
2666 }, _( "factions data" ) );
2667}
void write_to_file(const std::string &path, const std::function< void(std::ostream &)> &writer)
void serialize_master(std::ostream &fout)
Definition: savegame.cpp:1243

References _, get_world_base_save_path(), SAVE_MASTER(), serialize_master(), and write_to_file().

Referenced by cleanup_at_end(), and save().

◆ save_maps()

bool game::save_maps ( )
private

Definition at line 2675 of file game.cpp.

2676{
2677 try {
2678 m.save();
2679 overmap_buffer.save(); // can throw
2680 MAPBUFFER.save(); // can throw
2681 return true;
2682 } catch( const std::exception &err ) {
2683 popup( _( "Failed to save the maps: %s" ), err.what() );
2684 return false;
2685 }
2686}
void save(bool delete_after_save=false)
Store all submaps in this instance into savefiles.
Definition: mapbuffer.cpp:98

References _, m, MAPBUFFER, overmap_buffer, popup(), map::save(), overmapbuffer::save(), and mapbuffer::save().

Referenced by cleanup_at_end(), and save().

◆ save_player_data()

bool game::save_player_data ( )
private

Definition at line 2688 of file game.cpp.

2689{
2690 const std::string playerfile = get_player_base_save_path();
2691
2692 const bool saved_data = write_to_file( playerfile + SAVE_EXTENSION, [&]( std::ostream & fout ) {
2693 serialize( fout );
2694 }, _( "player data" ) );
2695 const bool saved_map_memory = u.save_map_memory();
2696 const bool saved_log = write_to_file( playerfile + SAVE_EXTENSION_LOG, [&](
2697 std::ostream & fout ) {
2698 fout << memorial().dump();
2699 }, _( "player memorial" ) );
2700#if defined(__ANDROID__)
2701 const bool saved_shortcuts = write_to_file( playerfile + SAVE_EXTENSION_SHORTCUTS, [&](
2702 std::ostream & fout ) {
2703 save_shortcuts( fout );
2704 }, _( "quick shortcuts" ) );
2705#endif
2706 const bool saved_diary = u.get_avatar_diary()->store();
2707 return saved_data && saved_map_memory && saved_log && saved_diary
2708#if defined(__ANDROID__)
2709 && saved_shortcuts
2710#endif
2711 ;
2712}
bool save_map_memory()
Definition: avatar.cpp:133
bool store()
Definition: diary.cpp:760
std::string get_player_base_save_path() const
Base path for saving player data.
Definition: game.cpp:12062
void serialize(std::ostream &fout)
Saving and loading functions.
Definition: savegame.cpp:69
std::string dump() const
Concatenates all of the memorial log entries, delimiting them with newlines, and returns the resultin...

References _, memorial_logger::dump(), avatar::get_avatar_diary(), get_player_base_save_path(), memorial(), SAVE_EXTENSION(), SAVE_EXTENSION_LOG(), SAVE_EXTENSION_SHORTCUTS(), avatar::save_map_memory(), serialize(), diary::store(), u, and write_to_file().

Referenced by save().

◆ serialize()

void game::serialize ( std::ostream &  fout)

Saving and loading functions.

Definition at line 69 of file savegame.cpp.

70{
71 /*
72 * Format version 12: Fully json, save the header. Weather and memorial exist elsewhere.
73 * To prevent (or encourage) confusion, there is no version 8. (cata 0.8 uses v7)
74 */
75 // Header
76 fout << "# version " << savegame_version << std::endl;
77
78 JsonOut json( fout, true ); // pretty-print
79
80 json.start_object();
81 // basic game state information.
82 json.member( "turn", calendar::turn );
84 json.member( "calendar_start", calendar_config._start_of_cataclysm );
85 json.member( "game_start", calendar_config._start_of_game );
86 json.member( "initial_season", static_cast<int>( calendar_config._initial_season ) );
87 json.member( "auto_travel_mode", auto_travel_mode );
88 json.member( "run_mode", static_cast<int>( safe_mode ) );
89 json.member( "mostseen", mostseen );
90 // current map coordinates
91 tripoint pos_sm = m.get_abs_sub();
92 const point pos_om = sm_to_om_remain( pos_sm.x, pos_sm.y );
93 json.member( "levx", pos_sm.x );
94 json.member( "levy", pos_sm.y );
95 json.member( "levz", pos_sm.z );
96 json.member( "om_x", pos_om.x );
97 json.member( "om_y", pos_om.y );
98
99 json.member( "grscent", scent.serialize() );
100 json.member( "typescent", scent.serialize( true ) );
101
102 // Then each monster
103 json.member( "active_monsters", *critter_tracker );
104 json.member( "stair_monsters", coming_to_stairs );
105
106 // save stats.
107 json.member( "kill_tracker", *kill_tracker_ptr );
108 json.member( "stats_tracker", *stats_tracker_ptr );
109 json.member( "achievements_tracker", *achievements_tracker_ptr );
110
111 json.member( "token_provider", *token_provider_ptr );
112
113 json.member( "player", u );
114 Messages::serialize( json );
115
116 json.end_object();
117}
Definition: json.h:575
A class that keeps time data other than current time.
Definition: calendar.h:530
season_type _initial_season
Definition: calendar.h:534
time_point _start_of_game
Definition: calendar.h:533
time_point _start_of_cataclysm
Definition: calendar.h:532
pimpl< drop_token_provider > token_provider_ptr
Definition: game.h:974
std::string serialize(bool is_type=false) const
Definition: savegame.cpp:119
point sm_to_om_remain(int &x, int &y)
void serialize(JsonOut &json)
Definition: messages.cpp:321
calendar_config config
const int savegame_version
Definition: savegame.cpp:57

References calendar_config::_initial_season, calendar_config::_start_of_cataclysm, calendar_config::_start_of_game, achievements_tracker_ptr, auto_travel_mode, coming_to_stairs, calendar::config, critter_tracker, JsonOut::end_object(), map::get_abs_sub(), kill_tracker_ptr, m, JsonOut::member(), mostseen, safe_mode, savegame_version, scent, scent_map::serialize(), Messages::serialize(), sm_to_om_remain(), JsonOut::start_object(), stats_tracker_ptr, token_provider_ptr, calendar::turn, u, point::x, tripoint::x, point::y, tripoint::y, and tripoint::z.

Referenced by save_player_data().

◆ serialize_master()

void game::serialize_master ( std::ostream &  fout)
private

Definition at line 1243 of file savegame.cpp.

1244{
1245 fout << "# version " << savegame_version << std::endl;
1246 try {
1247 JsonOut json( fout, true ); // pretty-print
1248 json.start_object();
1249
1250 json.member( "next_mission_id", next_mission_id );
1251 json.member( "next_npc_id", next_npc_id );
1252
1253 json.member( "active_missions" );
1254 mission::serialize_all( json );
1255
1256 json.member( "factions", *faction_manager_ptr );
1257 json.member( "seed", seed );
1258
1259 json.member( "weather" );
1260 json.start_object();
1261 json.member( "lightning", get_weather().lightning_active );
1262 json.end_object();
1263
1264 json.end_object();
1265 } catch( const JsonError &e ) {
1266 debugmsg( "error saving to %s: %s", SAVE_MASTER, e.c_str() );
1267 }
1268}
Definition: json.h:51
const char * c_str() const noexcept
Definition: json.h:54
static void serialize_all(JsonOut &json)
Definition: savegame.cpp:1234

References JsonError::c_str(), debugmsg, JsonOut::end_object(), faction_manager_ptr, get_weather, JsonOut::member(), next_mission_id, next_npc_id, SAVE_MASTER(), savegame_version, seed, mission::serialize_all(), and JsonOut::start_object().

Referenced by save_factions_missions_npcs().

◆ set_critter_died()

void game::set_critter_died ( )

If invoked, dead will be cleaned this turn.

Definition at line 1789 of file game.cpp.

1790{
1791 critter_died = true;
1792}

References critter_died.

◆ set_driving_view_offset()

void game::set_driving_view_offset ( point  p)

Definition at line 1599 of file game.cpp.

1600{
1601 // remove the previous driving offset,
1602 // store the new offset and apply the new offset.
1609}

References driving_view_offset, u, player::view_offset, point::x, tripoint::x, point::y, and tripoint::y.

Referenced by calc_driving_offset(), and cleanup_at_end().

◆ set_npcs_dirty()

void game::set_npcs_dirty ( )

If invoked, NPCs will be reloaded before next turn.

Definition at line 1784 of file game.cpp.

1785{
1786 npcs_dirty = true;
1787}

References npcs_dirty.

◆ set_safe_mode()

void game::set_safe_mode ( safe_mode_type  mode)

Definition at line 8652 of file game.cpp.

8653{
8654 safe_mode = mode;
8656}

References safe_mode, and safe_mode_warning_logged.

Referenced by handle_action(), and mon_info_update().

◆ set_zoom()

void game::set_zoom ( int  level)

Definition at line 7107 of file game.cpp.

7108{
7109#if defined(TILES)
7110 if( tileset_zoom != level ) {
7111 tileset_zoom = level;
7112 rescale_tileset( tileset_zoom );
7113 }
7114#else
7115 static_cast<void>( level );
7116#endif // TILES
7117}

References tileset_zoom.

Referenced by look_around().

◆ setremoteveh()

void game::setremoteveh ( vehicle veh)

Sets the current remotely controlled vehicle.

Definition at line 2274 of file game.cpp.

2275{
2277 remoteveh_cache = veh;
2278 if( veh != nullptr && !u.has_active_bionic( bio_remote ) &&
2280 debugmsg( "Tried to set remote vehicle without bio_remote or remotevehcontrol" );
2281 veh = nullptr;
2282 }
2283
2284 if( veh == nullptr ) {
2285 u.remove_value( "remote_controlling_vehicle" );
2286 return;
2287 }
2288
2289 std::stringstream remote_veh_string;
2290 const tripoint vehpos = veh->global_pos3();
2291 remote_veh_string << vehpos.x << ' ' << vehpos.y << ' ' << vehpos.z;
2292 u.set_value( "remote_controlling_vehicle", remote_veh_string.str() );
2293}
void remove_value(const std::string &key)
Definition: creature.cpp:1377

References bio_remote, debugmsg, vehicle::global_pos3(), Character::has_active_bionic(), Character::has_active_item(), itype_remotevehcontrol, remoteveh_cache, remoteveh_cache_time, Creature::remove_value(), Creature::set_value(), calendar::turn, u, tripoint::x, tripoint::y, and tripoint::z.

◆ setup()

void game::setup ( )

Definition at line 479 of file game.cpp.

480{
481 loading_ui ui( true );
482
484
485 if( get_option<bool>( "ELEVATED_BRIDGES" ) && !get_option<bool>( "ZLEVELS" ) ) {
486 debugmsg( "\"Elevated bridges\" mod requires z-levels to be ENABLED to work properly!" );
487 }
488
489 m = map( get_option<bool>( "ZLEVELS" ) );
490
492 next_mission_id = 1;
493 new_game = true;
494 uquit = QUIT_NO; // We haven't quit the game
495 bVMonsterLookFire = true;
496
497 // invalidate calendar caches in case we were previously playing
498 // a different world
499 calendar::set_eternal_season( ::get_option<bool>( "ETERNAL_SEASON" ) );
500 calendar::set_season_length( ::get_option<int>( "SEASON_LENGTH" ) );
501
504
505 turnssincelastmon = 0; //Auto safe mode init
506
509 coming_to_stairs.clear();
510 active_npc.clear();
511 faction_manager_ptr->clear();
516
517 SCT.vSCT.clear(); //Delete pending messages
518
519 stats().clear();
520 // reset kill counts
523 // reset follower list
524 follower_ids.clear();
525 scent.reset();
526
528 remoteveh_cache = nullptr;
529
530 token_provider_ptr->clear();
531 // back to menu for save loading, new game etc
532}
void clear_zombies()
Redirects to the creature_tracker clear() function.
Definition: game.cpp:4740
static void clear_all()
Remove all active missions, used to cleanup on exit and before reloading a new game.
Definition: mission.cpp:127
void reset()
Definition: scent_map.cpp:51
static const string_id< weather_type > & NULL_ID()
Returns a null id whose string_id<T>::is_null() must always return true.
void clear_messages()
Definition: messages.cpp:351
void load_world_modfiles(loading_ui &ui, const std::string &artifacts_file)
Load & finalize modlist needed for the current world.
Definition: init.cpp:933
void reset_sounds()
Definition: sounds.cpp:566

References achievements_tracker_ptr, active_npc, calendar::before_time_starts, bVMonsterLookFire, character_id, explosion_handler::explosion_queue::clear(), kill_tracker::clear(), stats_tracker::clear(), mission::clear_all(), Messages::clear_messages(), clear_zombies(), coming_to_stairs, debugmsg, faction_manager_ptr, follower_ids, explosion_handler::get_explosion_queue(), get_kill_tracker(), get_weather, get_world_base_save_path(), init::load_world_modfiles(), m, new_game, next_mission_id, next_npc_id, weather_manager::nextweather, string_id< weather_type >::NULL_ID(), QUIT_NO, remoteveh_cache, remoteveh_cache_time, scent_map::reset(), sounds::reset_sounds(), SAVE_ARTIFACTS(), scent, SCT, calendar::set_eternal_season(), calendar::set_season_length(), stats(), timed_events, token_provider_ptr, turnssincelastmon, uquit, scrollingcombattext::vSCT, and weather_manager::weather_id.

Referenced by butcher_submenu(), and quickload().

◆ shared_from()

template<typename T >
template shared_ptr_fast< npc > game::shared_from< npc > ( const T &  critter)

Returns a shared pointer to the given critter (which can be of any of the subclasses of Creature).

The function may return an empty pointer if the given critter is not stored anywhere (e.g. it was allocated on the stack, not stored in the critter_tracker nor in active_npc nor is it u).

Definition at line 4593 of file game.cpp.

4594{
4595 if( static_cast<const Creature *>( &critter ) == static_cast<const Creature *>( &u ) ) {
4596 // u is not stored in a shared_ptr, but it won't go out of scope anyway
4597 return std::dynamic_pointer_cast<T>( u_shared_ptr );
4598 }
4599 if( critter.is_monster() ) {
4600 if( const shared_ptr_fast<monster> mon_ptr = critter_tracker->find( critter.pos() ) ) {
4601 if( static_cast<const Creature *>( mon_ptr.get() ) == static_cast<const Creature *>( &critter ) ) {
4602 return std::dynamic_pointer_cast<T>( mon_ptr );
4603 }
4604 }
4605 }
4606 if( critter.is_npc() ) {
4607 for( auto &cur_npc : active_npc ) {
4608 if( static_cast<const Creature *>( cur_npc.get() ) == static_cast<const Creature *>( &critter ) ) {
4609 return std::dynamic_pointer_cast<T>( cur_npc );
4610 }
4611 }
4612 }
4613 return nullptr;
4614}

References active_npc, critter_tracker, u, and u_shared_ptr.

Referenced by list_monsters(), mon_info_update(), and validate_mounted_npcs().

◆ shift_destination_preview()

void game::shift_destination_preview ( point  delta)

Definition at line 12075 of file game.cpp.

12076{
12077 for( tripoint &p : destination_preview ) {
12078 p += delta;
12079 }
12080}

References destination_preview.

◆ shift_monsters()

void game::shift_monsters ( const tripoint shift)
private

Shift all active monsters, the shift vector is the number of shifted submaps.

Monsters that are outside of the reality bubble after shifting are despawned. Note on z-levels: this works with vertical shifts, but currently all monsters are despawned upon a vertical shift.

Definition at line 11064 of file game.cpp.

11065{
11066 // If either shift argument is non-zero, we're shifting.
11067 if( shift == tripoint_zero ) {
11068 return;
11069 }
11070 for( monster &critter : all_monsters() ) {
11071 if( shift.xy() != point_zero ) {
11072 critter.shift( shift.xy() );
11073 }
11074
11075 if( m.inbounds( critter.pos() ) && ( shift.z == 0 || m.has_zlevels() ) ) {
11076 // We're inbounds, so don't despawn after all.
11077 // No need to shift Z-coordinates, they are absolute
11078 continue;
11079 }
11080 // Either a vertical shift or the critter is now outside of the reality bubble,
11081 // anyway: it must be saved and removed.
11082 despawn_monster( critter );
11083 }
11084 // The order in which zombies are shifted may cause zombies to briefly exist on
11085 // the same square. This messes up the mon_at cache, so we need to rebuild it.
11086 critter_tracker->rebuild_cache();
11087}

References all_monsters(), critter_tracker, despawn_monster(), map::has_zlevels(), map::inbounds(), m, point_zero, tripoint_zero, tripoint::xy(), and tripoint::z.

Referenced by update_map(), vertical_move(), and vertical_shift().

◆ slip_down()

bool game::slip_down ( )

Checks if player is able to successfully climb to/from some terrain and not slip down.

Returns
whether player has slipped down
Dexterity decreases chances of slipping while climbing

Definition at line 12082 of file game.cpp.

12083{
12084 ///\EFFECT_DEX decreases chances of slipping while climbing
12085 int climb = u.dex_cur;
12086 if( u.has_trait( trait_BADKNEES ) ) {
12087 climb = climb / 2;
12088 }
12089 if( one_in( climb ) ) {
12090 add_msg( m_bad, _( "You slip while climbing and fall down again." ) );
12091 if( climb <= 1 ) {
12092 add_msg( m_bad, _( "Climbing is impossible in your current state." ) );
12093 }
12094 return true;
12095 }
12096 return false;
12097}
static const trait_id trait_BADKNEES("BADKNEES")

References _, add_msg(), Character::dex_cur, Character::has_trait(), m_bad, one_in(), trait_BADKNEES, and u.

◆ spawn_hallucination()

bool game::spawn_hallucination ( const tripoint p)

Spawns a hallucination at a determined position.

Attempts to spawn a hallucination at given location.

Returns false if the hallucination couldn't be spawned for whatever reason, such as a monster already in the target square.

Returns
Whether or not a hallucination was successfully spawned.

Definition at line 4751 of file game.cpp.

4752{
4753 if( one_in( 100 ) ) {
4754 shared_ptr_fast<npc> tmp = make_shared_fast<npc>();
4755 tmp->randomize( NC_HALLU );
4756 tmp->spawn_at_precise( { get_levx(), get_levy() }, p );
4757 if( !critter_at( p, true ) ) {
4759 load_npcs();
4760 return true;
4761 } else {
4762 return false;
4763 }
4764 }
4765
4767 const shared_ptr_fast<monster> phantasm = make_shared_fast<monster>( mt );
4768 phantasm->hallucination = true;
4769 phantasm->spawn( p );
4770
4771 //Don't attempt to place phantasms inside of other creatures
4772 if( !critter_at( phantasm->pos(), true ) ) {
4773 return critter_tracker->add( phantasm );
4774 } else {
4775 return false;
4776 }
4777}
mtype_id get_valid_hallucination() const
static MonsterGenerator & generator()
npc_class_id NC_HALLU("NC_HALLU")

References critter_at(), critter_tracker, MonsterGenerator::generator(), get_levx(), get_levy(), MonsterGenerator::get_valid_hallucination(), overmapbuffer::insert_npc(), load_npcs(), NC_HALLU, one_in(), and overmap_buffer.

◆ spell_events_subscriber()

spell_events & game::spell_events_subscriber ( )

Definition at line 2734 of file game.cpp.

2735{
2736 return *spell_events_ptr;
2737}

References spell_events_ptr.

◆ start_calendar()

void game::start_calendar ( )

Definition at line 11642 of file game.cpp.

11643{
11644 const bool scen_season = scen->has_flag( "SPR_START" ) || scen->has_flag( "SUM_START" ) ||
11645 scen->has_flag( "AUT_START" ) || scen->has_flag( "WIN_START" ) ||
11646 scen->has_flag( "SUM_ADV_START" );
11647
11649 if( scen_season ) {
11650 // Configured starting date overridden by scenario, calendar_config.start is left as Spring 1
11652 get_option<int>( "INITIAL_TIME" );
11653 calendar_config._start_of_game = calendar::turn_zero + 1_hours * get_option<int>( "INITIAL_TIME" );
11654 if( scen->has_flag( "SPR_START" ) ) {
11656 } else if( scen->has_flag( "SUM_START" ) ) {
11659 } else if( scen->has_flag( "AUT_START" ) ) {
11662 } else if( scen->has_flag( "WIN_START" ) ) {
11665 } else if( scen->has_flag( "SUM_ADV_START" ) ) {
11668 } else {
11669 debugmsg( "The Unicorn" );
11670 }
11671 } else {
11672 // No scenario, so use the starting date+time configured in world options
11673 int initial_days = get_option<int>( "INITIAL_DAY" );
11674 if( initial_days == -1 ) {
11675 // 0 - 363 for a 91 day season
11676 initial_days = rng( 0, get_option<int>( "SEASON_LENGTH" ) * 4 - 1 );
11677 }
11679
11680 // Determine the season based off how long the seasons are set to be
11681 // First take the number of season elapsed up to the starting date, then mod by 4 to get the season of the current year
11682 const int season_number = ( initial_days / get_option<int>( "SEASON_LENGTH" ) ) % 4;
11683 if( season_number == 0 ) {
11685 } else if( season_number == 1 ) {
11687 } else if( season_number == 2 ) {
11689 } else {
11691 }
11692
11694 + 1_hours * get_option<int>( "INITIAL_TIME" )
11695 + 1_days * get_option<int>( "SPAWN_DELAY" );
11696 }
11697
11699}
@ WINTER
Definition: calendar.h:21
@ AUTUMN
Definition: calendar.h:20
@ SUMMER
Definition: calendar.h:19
@ SPRING
Definition: calendar.h:18
time_duration season_length() const
Definition: calendar.h:569
const scenario * scen
Definition: game.h:981
bool has_flag(const std::string &flag) const
Such as a seasonal start, fiery start, surrounded start, etc.
Definition: scenario.cpp:438

References calendar_config::_initial_season, calendar_config::_start_of_cataclysm, calendar_config::_start_of_game, AUTUMN, calendar::config, debugmsg, scenario::has_flag(), rng(), scen, calendar_config::season_length(), SPRING, SUMMER, calendar::turn, calendar::turn_zero, and WINTER.

Referenced by start_game().

◆ start_game()

bool game::start_game ( )
private

Definition at line 558 of file game.cpp.

559{
560 if( !gamemode ) {
561 gamemode = std::make_unique<special_game>();
562 }
563
564 seed = rng_bits();
565 new_game = true;
568 safe_mode = ( get_option<bool>( "SAFEMODE" ) ? SAFE_MODE_ON : SAFE_MODE_OFF );
569 mostseen = 0; // ...and mostseen is 0, we haven't seen any monsters yet.
572
574
577 popup.message( "%s", _( "Please wait as we build your world" ) );
580
581 load_master();
582 u.setID( assign_npc_id() ); // should be as soon as possible, but *after* load_master
583
587 do {
588 omtstart = start_loc.find_player_initial_location();
589 if( omtstart == overmap::invalid_tripoint ) {
590 if( query_yn(
591 _( "Try again?\n\nIt may require several attempts until the game finds a valid starting location." ) ) ) {
594 } else {
595 return false;
596 }
597 }
598 } while( omtstart == overmap::invalid_tripoint );
599
600 start_loc.prepare_map( omtstart );
601
602 // Place vehicles spawned by scenario or profession, has to be placed very early to avoid bugs.
603 if( u.starting_vehicle &&
604 !place_vehicle_nearby( u.starting_vehicle, omtstart.xy(), 0, 30,
605 std::vector<std::string> {} ) ) {
606 debugmsg( "could not place starting vehicle" );
607 }
608
609 if( scen->has_map_extra() ) {
610 // Map extras can add monster spawn points and similar and should be done before the main
611 // map is loaded.
612 start_loc.add_map_extra( omtstart, scen->get_map_extra() );
613 }
614
615 // TODO: fix point types
616 tripoint lev = project_to<coords::sm>( omtstart ).raw();
617 // The player is centered in the map, but lev[xyz] refers to the top left point of the map
618 lev.x -= HALF_MAPSIZE;
619 lev.y -= HALF_MAPSIZE;
620 load_map( lev, /*pump_events=*/true );
621
624 // Do this after the map cache has been built!
625 start_loc.place_player( u );
626 // ...but then rebuild it, because we want visibility cache to avoid spawning monsters in sight
629 // Start the overmap with out immediate neighborhood visible, this needs to be after place_player
631 get_option<int>( "DISTANCE_INITIAL_VISIBILITY" ), 0 );
632
633 u.moves = 0;
634 if( u.has_trait( trait_PROF_FERAL ) ) {
636 }
637 u.process_turn(); // process_turn adds the initial move points
641 u.next_climate_control_check = calendar::before_time_starts; // Force recheck at startup
643
644 //Reset character safe mode/pickup rules
649
650 //Put some NPCs in there!
651 if( get_option<std::string>( "STARTING_NPC" ) == "always" ||
652 ( get_option<std::string>( "STARTING_NPC" ) == "scenario" &&
653 !g->scen->has_flag( "LONE_START" ) ) ) {
655 }
656 //Load NPCs. Set nearby npcs to active.
657 load_npcs();
658 // Spawn the monsters
659 const bool spawn_near =
660 get_option<bool>( "BLACK_ROAD" ) || g->scen->has_flag( "SUR_START" );
661 // Surrounded start ones
662 if( spawn_near ) {
663 start_loc.surround_with_monsters( omtstart, mongroup_id( "GROUP_ZOMBIE" ), 70 );
664 }
665
666 m.spawn_monsters( !spawn_near ); // Static monsters
667
668 // Make sure that no monsters are near the player
669 // This can happen in lab starts
670 if( !spawn_near ) {
671 for( monster &critter : all_monsters() ) {
672 if( rl_dist( critter.pos(), u.pos() ) <= 5 ||
673 m.clear_path( critter.pos(), u.pos(), 40, 1, 100 ) ) {
674 remove_zombie( critter );
675 }
676 }
677 }
678
679 //Create mutation_category_level
681 //Calculate mutation drench protection stats
684 if( scen->has_flag( "FIRE_START" ) ) {
685 start_loc.burn( omtstart, 3, 3 );
686 }
687 if( scen->has_flag( "INFECTED" ) ) {
689 }
690 if( scen->has_flag( "BAD_DAY" ) ) {
691 u.add_effect( effect_flu, 1000_minutes );
692 u.add_effect( effect_drunk, 270_minutes );
693 u.add_morale( MORALE_FEELING_BAD, -100, -100, 50_minutes, 50_minutes );
694 }
695 if( scen->has_flag( "HELI_CRASH" ) ) {
696 start_loc.handle_heli_crash( u );
697 bool success = false;
698 for( auto v : m.get_vehicles() ) {
699 std::string name = v.v->type.str();
700 std::string search = std::string( "helicopter" );
701 if( name.find( search ) != std::string::npos ) {
702 for( const vpart_reference &vp : v.v->get_any_parts( VPFLAG_CONTROLS ) ) {
703 const tripoint pos = vp.pos();
704 u.setpos( pos );
705
706 // Delete the items that would have spawned here from a "corpse"
707 for( auto sp : v.v->parts_at_relative( vp.mount(), true ) ) {
708 vehicle_stack here = v.v->get_items( sp );
709
710 for( auto iter = here.begin(); iter != here.end(); ) {
711 iter = here.erase( iter );
712 }
713 }
714
715 auto mons = critter_tracker->find( pos );
716 if( mons != nullptr ) {
717 critter_tracker->remove( *mons );
718 }
719
720 success = true;
721 break;
722 }
723 if( success ) {
724 v.v->name = "Bird Wreckage";
725 break;
726 }
727 }
728 }
729 }
730 if( scen->has_flag( "BORDERED" ) ) {
731 overmap &starting_om = get_cur_om();
732 for( int z = -OVERMAP_DEPTH; z <= OVERMAP_HEIGHT; z++ ) {
733 starting_om.place_special_forced( overmap_special_id( "world" ), { 0, 0, z },
735 }
736
737 }
738 for( auto &e : u.inv_dump() ) {
739 e->set_owner( g->u );
740 }
741 // Now that we're done handling coordinates, ensure the player's submap is in the center of the map
742 update_map( u );
743 // Profession pets
744 for( const mtype_id &elem : u.starting_pets ) {
745 if( monster *const mon = place_critter_around( elem, u.pos(), 5 ) ) {
746 mon->friendly = -1;
747 mon->add_effect( effect_pet, 1_turns, num_bp );
748 } else {
749 add_msg( m_debug, "cannot place starting pet, no space!" );
750 }
751 }
752 // Assign all of this scenario's missions to the player.
753 for( const mission_type_id &m : scen->missions() ) {
754 const auto mission = mission::reserve_new( m, character_id() );
755 mission->assign( u );
756 }
757 g->events().send<event_type::game_start>( u.getID() );
758 for( Skill &elem : Skill::skills ) {
759 int level = u.get_skill_level_object( elem.ident() ).level();
760 if( level > 0 ) {
761 g->events().send<event_type::gains_skill_level>( u.getID(), elem.ident(), level );
762 }
763 }
764 return true;
765}
body_part random_body_part(bool main_parts_only)
Returns a random body_part token.
Definition: bodypart.cpp:366
bool last_climate_control_ret
Definition: character.h:2298
SkillLevel & get_skill_level_object(const skill_id &ident)
Definition: character.cpp:3345
void drench_mut_calc()
Recalculates mutation drench protection for all bodyparts (ignored/good/neutral stats)
Definition: character.cpp:7817
void set_stamina(int new_stamina)
Definition: character.cpp:7103
time_point next_climate_control_check
Definition: character.h:2297
int get_stamina_max() const
Definition: character.cpp:7092
void set_highest_cat_level()
Recalculates mutation_category_level[] values for the player.
Definition: character.cpp:7794
void default_initialize()
Perform default initialization.
Definition: auto_note.cpp:101
void start_calendar()
Definition: game.cpp:11642
void create_starting_npcs()
Definition: game.cpp:888
overmap & get_cur_om() const
The overmap which contains the center submap of the reality bubble.
Definition: game.cpp:11942
vehicle * place_vehicle_nearby(const vproto_id &id, const point_abs_omt &origin, int min_distance, int max_distance, const std::vector< std::string > &omt_search_types={})
Definition: game.cpp:767
bool clear_path(const tripoint &f, const tripoint &t, int range, int cost_min, int cost_max) const
Check whether there's a direct line of sight between F and T with the additional movecost restraints.
Definition: map.cpp:6535
static mission * reserve_new(const mission_type_id &type, const character_id &npc_id)
Create a new mission of the given type and assign it to the given npc.
Definition: mission.cpp:64
void assign(avatar &u)
Assigns the mission to the player.
Definition: mission.cpp:210
void place_special_forced(const overmap_special_id &special_id, const tripoint_om_omt &p, om_direction::type dir)
Definition: overmap.cpp:2164
bool reveal(const point_abs_omt &center, int radius, int z)
Mark a square area around center on Z-level z as seen.
bool random_start_location
Definition: player.h:238
vproto_id starting_vehicle
Definition: player.h:250
std::vector< mtype_id > starting_pets
Definition: player.h:251
start_location_id start_location
Definition: player.h:239
void clear_character_rules()
bool has_map_extra() const
Definition: scenario.cpp:453
const std::string & get_map_extra() const
Definition: scenario.cpp:457
const std::vector< mission_type_id > & missions() const
Definition: scenario.cpp:461
start_location_id random_start_location() const
Definition: scenario.cpp:232
void burn(const tripoint_abs_omt &omtstart, size_t count, int rad) const
Burn random terrain / furniture with FLAMMABLE or FLAMMABLE_ASH tag.
void surround_with_monsters(const tripoint_abs_omt &omtstart, const mongroup_id &type, float expected_points) const
Adds surround start monsters.
void prepare_map(const tripoint_abs_omt &omtstart) const
Initialize the map at players start location using prepare_map.
void place_player(player &u) const
Place the player somewhere in the reality bubble (g->m).
void handle_heli_crash(player &u) const
tripoint_abs_omt find_player_initial_location() const
Find a suitable start location on the overmap.
void add_map_extra(const tripoint_abs_omt &omtstart, const std::string &map_extra) const
Adds a map extra, see map_extras.h and map_extras.cpp.
const T & obj() const
Returns the actual object this id refers to.
Definition: achievement.cpp:63
static const efftype_id effect_drunk("drunk")
static const efftype_id effect_infected("infected")
static const trait_id trait_PROF_FERAL("PROF_FERAL")
static const efftype_id effect_accumulated_mutagen("accumulated_mutagen")
static const efftype_id effect_flu("flu")
static const efftype_id effect_feral_killed_recently("feral_killed_recently")
static constexpr int SPRING_TEMPERATURE
Base starting spring temperature in F used for climate, weather and temperature calculation.
void update_weather()
Definition: weather.cpp:1056
const morale_type MORALE_FEELING_BAD("morale_feeling_bad")
static bool search(const ui_adaptor &om_ui, tripoint_abs_omt &curs, const tripoint_abs_omt &orig)
unsigned int rng_bits()
Definition: rng.cpp:12
string_id< overmap_special > overmap_special_id
Definition: type_id.h:137
string_id< MonsterGroup > mongroup_id
Definition: type_id.h:108
@ VPFLAG_CONTROLS
Definition: veh_type.h:41

References _, Creature::add_effect(), start_location::add_map_extra(), Character::add_morale(), add_msg(), all_monsters(), mission::assign(), assign_npc_id(), calendar::before_time_starts, map::build_map_cache(), start_location::burn(), character_id, auto_notes::auto_note_settings::clear(), mapbuffer::clear(), overmapbuffer::clear(), auto_pickup::player_settings::clear_character_rules(), safemode::clear_character_rules(), map::clear_path(), create_starting_npcs(), critter_tracker, debugmsg, auto_notes::auto_note_settings::default_initialize(), Character::drench_mut_calc(), effect_accumulated_mutagen, effect_drunk, effect_feral_killed_recently, effect_flu, effect_infected, effect_pet, start_location::find_player_initial_location(), g, gains_skill_level, game_start, gamemode, get_auto_notes_settings(), get_auto_pickup(), get_cur_om(), get_distraction_manager(), get_levz(), scenario::get_map_extra(), get_safemode(), Character::get_skill_level_object(), Character::get_stamina_max(), map::get_vehicles(), get_weather, Character::getID(), Character::global_omt_location(), HALF_MAPSIZE, start_location::handle_heli_crash(), scenario::has_flag(), scenario::has_map_extra(), Character::has_trait(), anonymous_namespace{iexamine_elevator.cpp}::elevator::here(), init_autosave(), Character::inv_dump(), overmap::invalid_tripoint, map::invalidate_map_cache(), Character::last_climate_control_ret, distraction_manager::distraction_manager_gui::load(), safemode::load_global(), load_map(), load_master(), load_npcs(), m, m_debug, MAPBUFFER, scenario::missions(), MORALE_FEELING_BAD, mostseen, Creature::moves, om_direction::name(), new_game, Character::next_climate_control_check, weather_manager::nextweather, om_direction::north, num_bp, string_id< T >::obj(), overmap_buffer, OVERMAP_DEPTH, OVERMAP_HEIGHT, place_critter_around(), start_location::place_player(), overmap::place_special_forced(), place_vehicle_nearby(), popup(), Character::pos(), start_location::prepare_map(), Character::process_turn(), query_yn(), random_body_part(), player::random_start_location, scenario::random_start_location(), ui_manager::redraw(), refresh_display(), remove_zombie(), mission::reserve_new(), overmapbuffer::reveal(), rl_dist(), rng_bits(), safe_mode, SAFE_MODE_OFF, SAFE_MODE_ON, scen, overmap_ui::search(), seed, Character::set_highest_cat_level(), Character::set_stamina(), Character::setID(), Character::setpos(), Skill::skills, map::spawn_monsters(), SPRING_TEMPERATURE, start_calendar(), player::start_location, player::starting_pets, player::starting_vehicle, behavior::success, start_location::surround_with_monsters(), weather_manager::temperature, trait_PROF_FERAL, calendar::turn, u, update_map(), weather_manager::update_weather(), VPFLAG_CONTROLS, tripoint::x, coords::coord_point< Point, Origin, Scale >::xy(), and tripoint::y.

◆ start_hauling()

void game::start_hauling ( const tripoint pos)

Definition at line 10427 of file game.cpp.

10428{
10429 // Find target items and quantities thereof for the new activity
10430 std::vector<item_location> target_items;
10431 std::vector<int> quantities;
10432
10433 map_stack items = m.i_at( pos );
10434 for( item &it : items ) {
10435 // Liquid cannot be picked up
10436 if( it.made_of( LIQUID ) ) {
10437 continue;
10438 }
10439 target_items.emplace_back( map_cursor( pos ), &it );
10440 // Quantity of 0 means move all
10441 quantities.push_back( 0 );
10442 }
10443
10444 if( target_items.empty() ) {
10445 // Nothing to haul
10446 return;
10447 }
10448
10449 // Whether the destination is inside a vehicle (not supported)
10450 const bool to_vehicle = false;
10451 // Destination relative to the player
10452 const tripoint relative_destination{};
10453
10455 target_items,
10456 quantities,
10457 to_vehicle,
10458 relative_destination
10459 ) ) );
10460}

References Character::assign_activity(), map::i_at(), LIQUID, m, and u.

Referenced by vertical_move(), and walk_move().

◆ stats()

stats_tracker & game::stats ( )

Definition at line 2719 of file game.cpp.

2720{
2721 return *stats_tracker_ptr;
2722}

References stats_tracker_ptr.

Referenced by death_screen(), handle_action(), setup(), and win().

◆ swap_critters()

bool game::swap_critters ( Creature a,
Creature b 
)

Swaps positions of two creatures.

Definition at line 4779 of file game.cpp.

4780{
4781 if( &a == &b ) {
4782 // No need to do anything, but print a debugmsg anyway
4783 debugmsg( "Tried to swap %s with itself", a.disp_name() );
4784 return true;
4785 }
4786 if( critter_at( a.pos() ) != &a ) {
4787 debugmsg( "Tried to swap when it would cause a collision between %s and %s.",
4788 b.disp_name(), critter_at( a.pos() )->disp_name() );
4789 return false;
4790 }
4791 if( critter_at( b.pos() ) != &b ) {
4792 debugmsg( "Tried to swap when it would cause a collision between %s and %s.",
4793 a.disp_name(), critter_at( b.pos() )->disp_name() );
4794 return false;
4795 }
4796 // Simplify by "sorting" the arguments
4797 // Only the first argument can be u
4798 // If swapping player/npc with a monster, monster is second
4799 bool a_first = a.is_player() ||
4800 ( a.is_npc() && !b.is_player() );
4801 Creature &first = a_first ? a : b;
4802 Creature &second = a_first ? b : a;
4803 // Possible options:
4804 // both first and second are monsters
4805 // second is a monster, first is a player or an npc
4806 // first is a player, second is an npc
4807 // both first and second are npcs
4808 if( first.is_monster() ) {
4809 monster *m1 = dynamic_cast< monster * >( &first );
4810 monster *m2 = dynamic_cast< monster * >( &second );
4811 if( m1 == nullptr || m2 == nullptr || m1 == m2 ) {
4812 debugmsg( "Couldn't swap two monsters" );
4813 return false;
4814 }
4815
4816 critter_tracker->swap_positions( *m1, *m2 );
4817 return true;
4818 }
4819
4820 player *u_or_npc = dynamic_cast< player * >( &first );
4821 player *other_npc = dynamic_cast< player * >( &second );
4822
4823 if( u_or_npc->in_vehicle ) {
4824 m.unboard_vehicle( u_or_npc->pos() );
4825 }
4826
4827 if( other_npc && other_npc->in_vehicle ) {
4828 m.unboard_vehicle( other_npc->pos() );
4829 }
4830
4831 tripoint temp = second.pos();
4832 second.setpos( first.pos() );
4833
4834 if( first.is_player() ) {
4835 walk_move( temp );
4836 } else {
4837 first.setpos( temp );
4838 if( m.veh_at( u_or_npc->pos() ).part_with_feature( VPFLAG_BOARDABLE, true ) ) {
4839 m.board_vehicle( u_or_npc->pos(), u_or_npc );
4840 }
4841 }
4842
4843 if( other_npc && m.veh_at( other_npc->pos() ).part_with_feature( VPFLAG_BOARDABLE, true ) ) {
4844 m.board_vehicle( other_npc->pos(), other_npc );
4845 }
4846 return true;
4847}
virtual bool is_monster() const
Definition: creature.h:101
virtual bool is_player() const
Definition: creature.h:92
virtual void setpos(const tripoint &pos)=0
bool walk_move(const tripoint &dest, bool via_ramp=false)
Definition: game.cpp:8797
constexpr double a
Definition: magic.cpp:1030
constexpr double b
Definition: magic.cpp:1031
@ VPFLAG_BOARDABLE
Definition: veh_type.h:39

References a, b, map::board_vehicle(), critter_at(), critter_tracker, debugmsg, Character::in_vehicle, Creature::is_monster(), Creature::is_player(), m, optional_vpart_position::part_with_feature(), Creature::pos(), Character::pos(), second, Creature::setpos(), map::unboard_vehicle(), map::veh_at(), VPFLAG_BOARDABLE, and walk_move().

Referenced by npc_menu().

◆ take_screenshot() [1/2]

bool game::take_screenshot ( ) const

Saves a screenshot of the current viewport, as a PNG file.

Filesystem location is derived from the current world and character.

Note
: Only works for SDL/TILES (otherwise the function returns false). A window (more precisely, a viewport) must already exist and the SDL renderer must be valid.
Returns
true if the screenshot generation was successful, false otherwise.

Definition at line 7176 of file game.cpp.

7177{
7178 popup( _( "This binary was not compiled with tiles support." ) );
7179 return false;
7180}

References _, and popup().

Referenced by do_turn().

◆ take_screenshot() [2/2]

bool game::take_screenshot ( const std::string &  file_path) const

Saves a screenshot of the current viewport, as a PNG file, to the given location.

Parameters
file_pathA full path to the file where the screenshot should be saved.
Note
: Only works for SDL/TILES (otherwise the function returns false). A window (more precisely, a viewport) must already exist and the SDL renderer must be valid.
Returns
true if the screenshot generation was successful, false otherwise.

Definition at line 7170 of file game.cpp.

7171{
7172 popup( _( "This binary was not compiled with tiles support." ) );
7173 return false;
7174}

References _, and popup().

◆ temp_exit_fullscreen()

void game::temp_exit_fullscreen ( )

Definition at line 457 of file game.cpp.

458{
459 if( fullscreen ) {
460 was_fullscreen = true;
462 } else {
463 was_fullscreen = false;
464 }
465}

References fullscreen, toggle_fullscreen(), and was_fullscreen.

Referenced by list_items_monsters(), and look_around().

◆ toggle_debug_hour_timer()

void game::toggle_debug_hour_timer ( )

Definition at line 11249 of file game.cpp.

11250{
11252}

References game::debug_hour_timer::toggle().

Referenced by handle_action(), and look_around().

◆ toggle_fullscreen()

void game::toggle_fullscreen ( )

Definition at line 410 of file game.cpp.

411{
412#if !defined(TILES)
415#else
416 toggle_fullscreen_window();
417#endif
418}

References fullscreen, and mark_main_ui_adaptor_resize().

Referenced by handle_action(), reenter_fullscreen(), and temp_exit_fullscreen().

◆ toggle_gate()

void game::toggle_gate ( const tripoint p)

Definition at line 5148 of file game.cpp.

5149{
5150 gates::toggle_gate( p, u );
5151}
void toggle_gate(const tripoint &pos, player &p)
opens/closes the gate via player's activity
Definition: gates.cpp:237

References gates::toggle_gate(), and u.

◆ toggle_pixel_minimap()

void game::toggle_pixel_minimap ( )

Definition at line 420 of file game.cpp.

421{
422#if defined(TILES)
424 clear_window_area( w_pixel_minimap );
425 }
428#endif // TILES
429}

References mark_main_ui_adaptor_resize(), pixel_minimap_option, and w_pixel_minimap.

Referenced by handle_action(), and look_around().

◆ try_get_left_click_action()

bool game::try_get_left_click_action ( action_id act,
const tripoint mouse_target 
)
private

Definition at line 2295 of file game.cpp.

2296{
2297 bool new_destination = true;
2298 if( !destination_preview.empty() ) {
2299 auto &final_destination = destination_preview.back();
2300 if( final_destination.x == mouse_target.x && final_destination.y == mouse_target.y ) {
2301 // Second click
2302 new_destination = false;
2304 destination_preview.clear();
2306 if( act == ACTION_NULL ) {
2307 // Something went wrong
2309 return false;
2310 }
2311 }
2312 }
2313
2314 if( new_destination ) {
2316 u.get_path_avoid() );
2317 return false;
2318 }
2319
2320 return true;
2321}

References act, ACTION_NULL, Character::clear_destination(), destination_preview, Character::get_next_auto_move_direction(), Character::get_path_avoid(), Character::get_pathfinding_settings(), m, Character::pos(), map::route(), Character::set_destination(), u, tripoint::x, and tripoint::y.

Referenced by handle_action().

◆ try_get_right_click_action()

bool game::try_get_right_click_action ( action_id act,
const tripoint mouse_target 
)
private

Definition at line 2323 of file game.cpp.

2324{
2325 const bool cleared_destination = !destination_preview.empty();
2327 destination_preview.clear();
2328
2329 if( cleared_destination ) {
2330 // Produce no-op if auto-move had just been cleared on this action
2331 // e.g. from a previous single left mouse click. This has the effect
2332 // of right-click canceling an auto-move before it is initiated.
2333 return false;
2334 }
2335
2336 const bool is_adjacent = square_dist( mouse_target.xy(), point( u.posx(), u.posy() ) ) <= 1;
2337 const bool is_self = square_dist( mouse_target.xy(), point( u.posx(), u.posy() ) ) <= 0;
2338 if( const monster *const mon = critter_at<monster>( mouse_target ) ) {
2339 if( !u.sees( *mon ) ) {
2340 add_msg( _( "Nothing relevant here." ) );
2341 return false;
2342 }
2343
2344 if( !u.primary_weapon().is_gun() ) {
2345 add_msg( m_info, _( "You are not wielding a ranged weapon." ) );
2346 return false;
2347 }
2348
2349 // TODO: Add weapon range check. This requires weapon to be reloaded.
2350
2351 act = ACTION_FIRE;
2352 } else if( is_adjacent &&
2353 m.close_door( tripoint( mouse_target.xy(), u.posz() ), !m.is_outside( u.pos() ),
2354 true ) ) {
2355 act = ACTION_CLOSE;
2356 } else if( is_self ) {
2358 } else if( is_adjacent ) {
2360 } else {
2361 add_msg( _( "Nothing relevant here." ) );
2362 return false;
2363 }
2364
2365 return true;
2366}
bool close_door(const tripoint &p, bool inside, bool check_only)
Definition: map.cpp:4094
static bool is_adjacent(const monster &z, const Creature &target)

References _, act, ACTION_CLOSE, ACTION_EXAMINE, ACTION_FIRE, ACTION_PICKUP, add_msg(), Character::clear_destination(), map::close_door(), destination_preview, is_adjacent(), item::is_gun(), map::is_outside(), m, m_info, Character::pos(), Character::posx(), Character::posy(), Character::posz(), Character::primary_weapon(), Character::sees(), square_dist(), u, and tripoint::xy().

Referenced by handle_action().

◆ unload_npcs()

void game::unload_npcs ( )
private

Unloads all NPCs.

If you call this you must later call load_npcs, lest caches get rather confused. The tests used to call this a lot when they shouldn't. It is now private to reduce the chance of similar problems in the future.

Definition at line 871 of file game.cpp.

872{
873 for( const auto &npc : active_npc ) {
874 npc->on_unload();
875 }
876
877 active_npc.clear();
878}
void on_unload()
Do some cleanup and caching as npc is being unloaded from map.
Definition: npc.cpp:2668

References active_npc, and npc::on_unload().

Referenced by place_player_overmap(), and reload_npcs().

◆ unserialize()

void game::unserialize ( std::istream &  fin)

Definition at line 167 of file savegame.cpp.

168{
169 chkversion( fin );
170 int tmpturn = 0;
171 int tmpcalstart = 0;
172 int tmprun = 0;
173 tripoint lev;
174 point com;
175 JsonIn jsin( fin );
176 try {
177 JsonObject data = jsin.get_object();
178
179 data.read( "turn", tmpturn );
180 data.read( "calendar_start", tmpcalstart );
182 calendar_config._initial_season = static_cast<season_type>( data.get_int( "initial_season",
183 static_cast<int>( SPRING ) ) );
184 // 0.E stable
185 if( savegame_loading_version < 26 ) {
186 tmpturn *= 6;
187 tmpcalstart *= 6;
188 }
191 tmpcalstart );
192
193 if( !data.read( "game_start", calendar_config._start_of_game ) ) {
195 }
196
197 data.read( "auto_travel_mode", auto_travel_mode );
198 data.read( "run_mode", tmprun );
199 data.read( "mostseen", mostseen );
200 data.read( "levx", lev.x );
201 data.read( "levy", lev.y );
202 data.read( "levz", lev.z );
203 data.read( "om_x", com.x );
204 data.read( "om_y", com.y );
205
206 load_map(
207 tripoint( lev.x + com.x * OMAPX * 2, lev.y + com.y * OMAPY * 2, lev.z ),
208 /*pump_events=*/true
209 );
210
211 safe_mode = static_cast<safe_mode_type>( tmprun );
212 if( get_option<bool>( "SAFEMODE" ) && safe_mode == SAFE_MODE_OFF ) {
214 }
215
216 std::string linebuff;
217 std::string linebuf;
218 if( data.read( "grscent", linebuf ) && data.read( "typescent", linebuff ) ) {
219 scent.deserialize( linebuf );
220 scent.deserialize( linebuff, true );
221 } else {
222 scent.reset();
223 }
224 data.read( "active_monsters", *critter_tracker );
225
226 coming_to_stairs.clear();
227 for( auto elem : data.get_array( "stair_monsters" ) ) {
228 monster stairtmp;
229 elem.read( stairtmp );
230 coming_to_stairs.push_back( stairtmp );
231 }
232
233 if( data.has_object( "kill_tracker" ) ) {
234 data.read( "kill_tracker", *kill_tracker_ptr );
235 } else {
236 // Legacy support for when kills were stored directly in game
237 std::map<mtype_id, int> kills;
238 std::vector<std::string> npc_kills;
239 for( const JsonMember member : data.get_object( "kills" ) ) {
240 kills[mtype_id( member.name() )] = member.get_int();
241 }
242
243 for( const std::string npc_name : data.get_array( "npc_kills" ) ) {
244 npc_kills.push_back( npc_name );
245 }
246
247 kill_tracker_ptr->reset( kills, npc_kills );
248 }
249
250 data.read( "player", u );
252 data.read( "stats_tracker", *stats_tracker_ptr );
253 data.read( "achievements_tracker", *achievements_tracker_ptr );
254 data.read( "token_provider", token_provider_ptr );
256 Messages::deserialize( data );
257
258 } catch( const JsonError &jsonerr ) {
259 debugmsg( "Bad save json\n%s", jsonerr.c_str() );
260 return;
261 }
262}
season_type
Real world seasons.
Definition: calendar.h:17
Represents a member of a JsonObject.
Definition: json.h:1249
JsonObject get_object(const std::string &name) const
Definition: json.cpp:429
bool has_object(const std::string &name) const
Definition: json.cpp:493
JsonArray get_array(const std::string &name) const
Definition: json.cpp:400
int get_int(const std::string &name) const
Definition: json.cpp:350
bool read(const std::string &name, T &t, bool throw_on_error=true) const
Definition: json.h:941
void deserialize(const std::string &data, bool is_type=false)
Definition: savegame.cpp:264
safe_mode_type
Definition: game.h:76
static constexpr int OMAPY
static constexpr int OMAPX
Size of the overmap.
void deserialize(const JsonObject &json)
Definition: messages.cpp:330
std::string member
Definition: mapgen.cpp:419
static void chkversion(std::istream &fin)
Definition: savegame.cpp:148
int savegame_loading_version
Definition: savegame.cpp:64

References calendar_config::_initial_season, calendar_config::_start_of_cataclysm, calendar_config::_start_of_game, achievements_tracker_ptr, auto_travel_mode, JsonError::c_str(), chkversion(), coming_to_stairs, calendar::config, critter_tracker, debugmsg, Messages::deserialize(), scent_map::deserialize(), time_duration::from_turns(), JsonObject::get_array(), JsonObject::get_int(), JsonIn::get_object(), JsonObject::get_object(), JsonObject::has_object(), inp_mngr, kill_tracker_ptr, load_map(), mapgen_defer::member, mostseen, mtype_id, OMAPX, OMAPY, input_manager::pump_events(), JsonObject::read(), scent_map::reset(), safe_mode, SAFE_MODE_OFF, SAFE_MODE_ON, savegame_loading_version, scent, SPRING, stats_tracker_ptr, token_provider_ptr, calendar::turn, calendar::turn_zero, u, point::x, tripoint::x, point::y, tripoint::y, and tripoint::z.

Referenced by load().

◆ unserialize_master()

void game::unserialize_master ( std::istream &  fin)

Definition at line 1193 of file savegame.cpp.

1194{
1196 chkversion( fin );
1197 if( savegame_loading_version < 11 ) {
1198 std::unique_ptr<static_popup>popup = std::make_unique<static_popup>();
1199 popup->message(
1200 _( "Cannot find loader for save data in old version %d, attempting to load as current version %d." ),
1204 }
1205 try {
1206 // single-pass parsing example
1207 JsonIn jsin( fin );
1208 jsin.start_object();
1209 while( !jsin.end_object() ) {
1210 std::string name = jsin.get_member_name();
1211 if( name == "next_mission_id" ) {
1212 next_mission_id = jsin.get_int();
1213 } else if( name == "next_npc_id" ) {
1214 next_npc_id.deserialize( jsin );
1215 } else if( name == "active_missions" ) {
1217 } else if( name == "factions" ) {
1218 jsin.read( *faction_manager_ptr );
1219 } else if( name == "seed" ) {
1220 jsin.read( seed );
1221 } else if( name == "weather" ) {
1222 JsonObject w = jsin.get_object();
1223 w.read( "lightning", get_weather().lightning_active );
1224 } else {
1225 // silently ignore anything else
1226 jsin.skip_value();
1227 }
1228 }
1229 } catch( const JsonError &e ) {
1230 debugmsg( "error loading %s: %s", SAVE_MASTER, e.c_str() );
1231 }
1232}
void deserialize(JsonIn &)
static void unserialize_all(JsonIn &jsin)
Definition: savegame.cpp:1183

References _, JsonError::c_str(), chkversion(), debugmsg, character_id::deserialize(), JsonIn::end_object(), faction_manager_ptr, JsonIn::get_int(), JsonIn::get_member_name(), JsonIn::get_object(), get_weather, om_direction::name(), next_mission_id, next_npc_id, popup(), JsonIn::read(), JsonObject::read(), ui_manager::redraw(), refresh_display(), SAVE_MASTER(), savegame_loading_version, savegame_version, seed, JsonIn::skip_value(), JsonIn::start_object(), and mission::unserialize_all().

Referenced by load_master().

◆ update_map() [1/2]

point game::update_map ( int &  x,
int &  y 
)

Definition at line 10695 of file game.cpp.

10696{
10697 point shift;
10698
10699 while( x < HALF_MAPSIZE_X ) {
10700 x += SEEX;
10701 shift.x--;
10702 }
10703 while( x >= HALF_MAPSIZE_X + SEEX ) {
10704 x -= SEEX;
10705 shift.x++;
10706 }
10707 while( y < HALF_MAPSIZE_Y ) {
10708 y += SEEY;
10709 shift.y--;
10710 }
10711 while( y >= HALF_MAPSIZE_Y + SEEY ) {
10712 y -= SEEY;
10713 shift.y++;
10714 }
10715
10716 if( shift == point_zero ) {
10717 // adjust player position
10718 u.setpos( tripoint( x, y, get_levz() ) );
10719 // Update what parts of the world map we can see
10720 // We need this call because even if the map hasn't shifted we may have changed z-level and can now see farther
10721 // TODO: only make this call if we changed z-level
10723 // Not actually shifting the submaps, all the stuff below would do nothing
10724 return point_zero;
10725 }
10726
10727 // this handles loading/unloading submaps that have scrolled on or off the viewport
10728 // NOLINTNEXTLINE(cata-use-named-point-constants)
10729 inclusive_rectangle<point> size_1( point( -1, -1 ), point( 1, 1 ) );
10730 point remaining_shift = shift;
10731 while( remaining_shift != point_zero ) {
10732 point this_shift = clamp( remaining_shift, size_1 );
10733 m.shift( this_shift );
10734 remaining_shift -= this_shift;
10735 }
10736
10737 grid_tracker_ptr->load( m );
10738
10739 // Shift monsters
10740 shift_monsters( tripoint( shift, 0 ) );
10741 const point shift_ms = sm_to_ms_copy( shift );
10742 u.shift_destination( -shift_ms );
10743
10744 // Shift NPCs
10745 for( auto it = active_npc.begin(); it != active_npc.end(); ) {
10746 ( *it )->shift( shift );
10747 if( ( *it )->posx() < 0 - SEEX * 2 || ( *it )->posy() < 0 - SEEX * 2 ||
10748 ( *it )->posx() > SEEX * ( MAPSIZE + 2 ) || ( *it )->posy() > SEEY * ( MAPSIZE + 2 ) ) {
10749 //Remove the npc from the active list. It remains in the overmap list.
10750 ( *it )->on_unload();
10751 it = active_npc.erase( it );
10752 } else {
10753 it++;
10754 }
10755 }
10756
10757 scent.shift( shift_ms );
10758
10759 // Also ensure the player is on current z-level
10760 // get_levz() should later be removed, when there is no longer such a thing
10761 // as "current z-level"
10762 u.setpos( tripoint( x, y, get_levz() ) );
10763
10764 // Only do the loading after all coordinates have been shifted.
10765
10766 // Check for overmap saved npcs that should now come into view.
10767 // Put those in the active list.
10768 load_npcs();
10769
10770 // Make sure map cache is consistent since it may have shifted.
10771 if( m.has_zlevels() ) {
10772 for( int zlev = -OVERMAP_DEPTH; zlev <= OVERMAP_HEIGHT; ++zlev ) {
10773 m.invalidate_map_cache( zlev );
10774 }
10775 } else {
10777 }
10779
10780 // Spawn monsters if appropriate
10781 // This call will generate new monsters in addition to loading, so it's placed after NPC loading
10782 m.spawn_monsters( false ); // Static monsters
10783
10784 // Update what parts of the world map we can see
10786
10787 return shift;
10788}
void shift_destination(point shift)
void shift_monsters(const tripoint &shift)
Shift all active monsters, the shift vector is the number of shifted submaps.
Definition: game.cpp:11064
void shift(point s)
Shift the map along the vector s.
Definition: map.cpp:6907
void shift(point sm_shift)
Definition: scent_map.cpp:82
point sm_to_ms_copy(point p)
static constexpr int HALF_MAPSIZE_Y
static constexpr int HALF_MAPSIZE_X

References active_npc, map::build_map_cache(), clamp(), get_levz(), grid_tracker_ptr, HALF_MAPSIZE_X, HALF_MAPSIZE_Y, map::has_zlevels(), map::invalidate_map_cache(), load_npcs(), m, MAPSIZE, OVERMAP_DEPTH, OVERMAP_HEIGHT, point_zero, scent, SEEX, SEEY, Character::setpos(), map::shift(), scent_map::shift(), Character::shift_destination(), shift_monsters(), sm_to_ms_copy(), map::spawn_monsters(), u, update_overmap_seen(), point::x, and point::y.

◆ update_map() [2/2]

point game::update_map ( player p)

Definition at line 10689 of file game.cpp.

10690{
10691 point p2( p.posx(), p.posy() );
10692 return update_map( p2.x, p2.y );
10693}

References Character::posx(), Character::posy(), update_map(), point::x, and point::y.

Referenced by fling_creature(), load(), place_player(), start_game(), update_map(), and vertical_move().

◆ update_overmap_seen()

void game::update_overmap_seen ( )

Definition at line 10790 of file game.cpp.

10791{
10792 const tripoint_abs_omt ompos = u.global_omt_location();
10793 const int dist = u.overmap_sight_range( light_level( u.posz() ) );
10794 const int dist_squared = dist * dist;
10795 // We can always see where we're standing
10796 overmap_buffer.set_seen( ompos, true );
10797 for( const tripoint_abs_omt &p : points_in_radius( ompos, dist ) ) {
10798 const point_rel_omt delta = p.xy() - ompos.xy();
10799 const int h_squared = delta.x() * delta.x() + delta.y() * delta.y();
10800 if( trigdist && h_squared > dist_squared ) {
10801 continue;
10802 }
10803 if( delta == point_rel_omt() ) {
10804 // 1. This case is already handled outside of the loop
10805 // 2. Calculating multiplier would cause division by zero
10806 continue;
10807 }
10808 // If circular distances are enabled, scale overmap distances by the diagonality of the sight line.
10809 point abs_delta = delta.raw().abs();
10810 int max_delta = std::max( abs_delta.x, abs_delta.y );
10811 const float multiplier = trigdist ? std::sqrt( h_squared ) / max_delta : 1;
10812 const std::vector<tripoint_abs_omt> line = line_to( ompos, p );
10813 float sight_points = dist;
10814 for( auto it = line.begin();
10815 it != line.end() && sight_points >= 0; ++it ) {
10816 const oter_id &ter = overmap_buffer.ter( *it );
10817 sight_points -= static_cast<int>( ter->get_see_cost() ) * multiplier;
10818 }
10819 if( sight_points >= 0 ) {
10820 tripoint_abs_omt seen( p );
10821 do {
10822 overmap_buffer.set_seen( seen, true );
10823 --seen.z();
10824 } while( seen.z() >= 0 );
10825 }
10826 }
10827}
bool trigdist
Circular distances.
int overmap_sight_range(int light_level) const
Returns the distance the player can see on the overmap.
Definition: character.cpp:659
constexpr Point & raw()
Definition: coordinates.h:111
void set_seen(const tripoint_abs_omt &p, bool seen=true)
coords::coord_point< point, coords::origin::relative, coords::omt > point_rel_omt
Definition: coordinates.h:478
tripoint_range< Tripoint > points_in_radius(const Tripoint &center, const int radius, const int radiusz=0)
Definition: map_iterator.h:125
unsigned char get_see_cost() const
Definition: omdata.h:230

References oter_t::get_see_cost(), Character::global_omt_location(), light_level(), line(), line_to(), overmap_buffer, Character::overmap_sight_range(), points_in_radius(), Character::posz(), coords::coord_point< Point, Origin, Scale >::raw(), overmapbuffer::set_seen(), overmapbuffer::ter(), trigdist, u, coords::coord_point< Point, Origin, Scale >::x(), point::x, coords::coord_point< Point, Origin, Scale >::xy(), coords::coord_point< Point, Origin, Scale >::y(), point::y, and coords::coord_point< Point, Origin, Scale >::z().

Referenced by place_player_overmap(), and update_map().

◆ update_stair_monsters()

void game::update_stair_monsters ( )
private
Dodge reduces chance of being downed when pushed off the stairs

Definition at line 10842 of file game.cpp.

10843{
10844 // Search for the stairs closest to the player.
10845 std::vector<int> stairx;
10846 std::vector<int> stairy;
10847 std::vector<int> stairdist;
10848
10849 const bool from_below = monstairz < get_levz();
10850
10851 if( coming_to_stairs.empty() ) {
10852 return;
10853 }
10854
10855 if( m.has_zlevels() ) {
10856 debugmsg( "%d monsters coming to stairs on a map with z-levels",
10857 coming_to_stairs.size() );
10858 coming_to_stairs.clear();
10859 }
10860
10861 for( const tripoint &dest : m.points_on_zlevel( u.posz() ) ) {
10862 if( ( from_below && m.has_flag( "GOES_DOWN", dest ) ) ||
10863 ( !from_below && m.has_flag( "GOES_UP", dest ) ) ) {
10864 stairx.push_back( dest.x );
10865 stairy.push_back( dest.y );
10866 stairdist.push_back( rl_dist( dest, u.pos() ) );
10867 }
10868 }
10869 if( stairdist.empty() ) {
10870 return; // Found no stairs?
10871 }
10872
10873 // Find closest stairs.
10874 size_t si = 0;
10875 for( size_t i = 0; i < stairdist.size(); i++ ) {
10876 if( stairdist[i] < stairdist[si] ) {
10877 si = i;
10878 }
10879 }
10880
10881 // Find up to 4 stairs for distance stairdist[si] +1
10882 std::vector<int> nearest;
10883 nearest.push_back( si );
10884 for( size_t i = 0; i < stairdist.size() && nearest.size() < 4; i++ ) {
10885 if( ( i != si ) && ( stairdist[i] <= stairdist[si] + 1 ) ) {
10886 nearest.push_back( i );
10887 }
10888 }
10889 // Randomize the stair choice
10890 si = random_entry_ref( nearest );
10891
10892 // Attempt to spawn zombies.
10893 for( size_t i = 0; i < coming_to_stairs.size(); i++ ) {
10894 point mpos( stairx[si], stairy[si] );
10895 monster &critter = coming_to_stairs[i];
10896 const tripoint dest {
10897 mpos, g->get_levz()
10898 };
10899
10900 // We might be not be visible.
10901 if( ( critter.posx() < 0 - ( MAPSIZE_X ) / 6 ||
10902 critter.posy() < 0 - ( MAPSIZE_Y ) / 6 ||
10903 critter.posx() > ( MAPSIZE_X * 7 ) / 6 ||
10904 critter.posy() > ( MAPSIZE_Y * 7 ) / 6 ) ) {
10905 continue;
10906 }
10907
10908 critter.staircount -= 4;
10909 // Let the player know zombies are trying to come.
10910 if( u.sees( dest ) ) {
10911 std::string dump;
10912 if( critter.staircount > 4 ) {
10913 dump += string_format( _( "You see a %s on the stairs" ), critter.name() );
10914 } else {
10915 if( critter.staircount > 0 ) {
10916 dump += ( from_below ?
10917 //~ The <monster> is almost at the <bottom/top> of the <terrain type>!
10918 string_format( _( "The %1$s is almost at the top of the %2$s!" ),
10919 critter.name(),
10920 m.tername( dest ) ) :
10921 string_format( _( "The %1$s is almost at the bottom of the %2$s!" ),
10922 critter.name(),
10923 m.tername( dest ) ) );
10924 }
10925 }
10926
10927 add_msg( m_warning, dump );
10928 } else {
10930 _( "a sound nearby from the stairs!" ), true, "misc", "stairs_movement" );
10931 }
10932
10933 if( critter.staircount > 0 ) {
10934 continue;
10935 }
10936
10937 if( is_empty( dest ) ) {
10938 critter.spawn( dest );
10939 critter.staircount = 0;
10940 place_critter_at( make_shared_fast<monster>( critter ), dest );
10941 if( u.sees( dest ) ) {
10942 if( !from_below ) {
10943 add_msg( m_warning, _( "The %1$s comes down the %2$s!" ),
10944 critter.name(),
10945 m.tername( dest ) );
10946 } else {
10947 add_msg( m_warning, _( "The %1$s comes up the %2$s!" ),
10948 critter.name(),
10949 m.tername( dest ) );
10950 }
10951 }
10952 coming_to_stairs.erase( coming_to_stairs.begin() + i );
10953 continue;
10954 } else if( u.pos() == dest ) {
10955 // Monster attempts to push player of stairs
10957 int tries = 0;
10958
10959 // the critter is now right on top of you and will attack unless
10960 // it can find a square to push you into with one of his tries.
10961 const int creature_push_attempts = 9;
10962 const int player_throw_resist_chance = 3;
10963
10964 critter.spawn( dest );
10965 while( tries < creature_push_attempts ) {
10966 tries++;
10967 push.x = rng( -1, 1 );
10968 push.y = rng( -1, 1 );
10969 point ipos( mpos + push );
10970 tripoint pos( ipos, get_levz() );
10971 if( ( push.x != 0 || push.y != 0 ) && !critter_at( pos ) &&
10972 critter.can_move_to( pos ) ) {
10973 bool resiststhrow = ( u.is_throw_immune() ) ||
10975 if( resiststhrow && one_in( player_throw_resist_chance ) ) {
10976 u.moves -= 25; // small charge for avoiding the push altogether
10977 add_msg( _( "The %s fails to push you back!" ),
10978 critter.name() );
10979 return; //judo or leg brace prevent you from getting pushed at all
10980 }
10981 // Not accounting for tentacles latching on, so..
10982 // Something is about to happen, lets charge half a move
10983 u.moves -= 50;
10984 if( resiststhrow && ( u.is_throw_immune() ) ) {
10985 //we have a judoka who isn't getting pushed but counterattacking now.
10986 mattack::thrown_by_judo( &critter );
10987 return;
10988 }
10989 std::string msg;
10990 ///\EFFECT_DODGE reduces chance of being downed when pushed off the stairs
10991 if( !( resiststhrow ) && ( u.get_dodge() + rng( 0, 3 ) < 12 ) ) {
10992 // dodge 12 - never get downed
10993 // 11.. avoid 75%; 10.. avoid 50%; 9.. avoid 25%
10994 u.add_effect( effect_downed, 2_turns );
10995 msg = _( "The %s pushed you back hard!" );
10996 } else {
10997 msg = _( "The %s pushed you back!" );
10998 }
10999 add_msg( m_warning, msg.c_str(), critter.name() );
11000 u.setx( u.posx() + push.x );
11001 u.sety( u.posy() + push.y );
11002 return;
11003 }
11004 }
11006 _( "The %s tried to push you back but failed! It attacks you!" ),
11007 critter.name() );
11008 critter.melee_attack( u );
11009 u.moves -= 50;
11010 return;
11011 } else if( monster *const mon_ptr = critter_at<monster>( dest ) ) {
11012 // Monster attempts to displace a monster from the stairs
11013 monster &other = *mon_ptr;
11014 critter.spawn( dest );
11015
11016 // the critter is now right on top of another and will push it
11017 // if it can find a square to push it into inside of his tries.
11018 const int creature_push_attempts = 9;
11019 const int creature_throw_resist = 4;
11020
11021 int tries = 0;
11022 point push2;
11023 while( tries < creature_push_attempts ) {
11024 tries++;
11025 push2.x = rng( -1, 1 );
11026 push2.y = rng( -1, 1 );
11027 point ipos2( mpos + push2 );
11028 tripoint pos( ipos2, get_levz() );
11029 if( ( push2.x == 0 && push2.y == 0 ) || ( ( ipos2.x == u.posx() ) && ( ipos2.y == u.posy() ) ) ) {
11030 continue;
11031 }
11032 if( !critter_at( pos ) && other.can_move_to( pos ) ) {
11033 other.setpos( tripoint( ipos2, get_levz() ) );
11034 other.moves -= 50;
11035 std::string msg;
11036 if( one_in( creature_throw_resist ) ) {
11037 other.add_effect( effect_downed, 2_turns );
11038 msg = _( "The %1$s pushed the %2$s hard." );
11039 } else {
11040 msg = _( "The %1$s pushed the %2$s." );
11041 }
11042 add_msg( m_neutral, msg, critter.name(), other.name() );
11043 return;
11044 }
11045 }
11046 return;
11047 }
11048 }
11049}
void setx(int x)
Definition: character.h:806
void sety(int y)
Definition: character.h:809
bool is_throw_immune() const
Returns true if the player is immune to throws.
float get_dodge() const override
Definition: melee.cpp:866
int monstairz
Definition: game.h:983
tripoint_range< tripoint > points_on_zlevel() const
Yields a range of all points that are contained in the map and have the z-level of this map (abs_sub)...
Definition: map.cpp:8783
bool can_move_to(const tripoint &p) const
Checks whether we can move to/through p.
Definition: monmove.cpp:261
int posy() const override
Definition: monster.h:498
void melee_attack(Creature &target)
Definition: monster.cpp:1420
int staircount
Definition: monster.h:509
void spawn(const tripoint &p)
Definition: monster.cpp:478
int posx() const override
Definition: monster.h:495
bool thrown_by_judo(monster *z)
Definition: monattack.cpp:4675
std::enable_if<!is_std_array< C >::value, constV & >::type random_entry_ref(const C &container)
Same as above, but with a statically allocated default value (using the default constructor).
Definition: rng.h:149

References _, Creature::add_effect(), add_msg(), monster::can_move_to(), coming_to_stairs, critter_at(), debugmsg, anonymous_namespace{iexamine_elevator.cpp}::elevator::dest(), effect_downed, g, Character::get_dodge(), get_levz(), map::has_flag(), Character::has_trait(), map::has_zlevels(), is_empty(), Character::is_throw_immune(), m, m_neutral, m_warning, MAPSIZE_X, MAPSIZE_Y, monster::melee_attack(), monstairz, sounds::movement, Creature::moves, monster::name(), one_in(), other, place_critter_at(), point_north_west, map::points_on_zlevel(), Character::pos(), Character::posx(), monster::posx(), Character::posy(), monster::posy(), Character::posz(), monexamine::push(), random_entry_ref(), rl_dist(), rng(), Character::sees(), Character::setx(), Character::sety(), sounds::sound(), monster::spawn(), monster::staircount, string_format(), map::tername(), mattack::thrown_by_judo(), trait_LEG_TENT_BRACE, u, point::x, and point::y.

Referenced by do_turn(), and vertical_move().

◆ update_zombie_pos()

bool game::update_zombie_pos ( const monster critter,
const tripoint pos 
)

Redirects to the creature_tracker update_pos() function.

Definition at line 4730 of file game.cpp.

4731{
4732 return critter_tracker->update_pos( critter, pos );
4733}

References critter_tracker.

◆ use_computer()

void game::use_computer ( const tripoint p)

Checks to see if a player can use a computer (not illiterate, etc.) and uses if able.

Definition at line 4513 of file game.cpp.

4514{
4515 if( u.has_trait( trait_id( "ILLITERATE" ) ) ) {
4516 add_msg( m_info, _( "You can not read a computer screen!" ) );
4517 return;
4518 }
4519 if( u.is_blind() ) {
4520 // we don't have screen readers in game
4521 add_msg( m_info, _( "You can not see a computer screen!" ) );
4522 return;
4523 }
4524 if( u.has_trait( trait_id( "HYPEROPIC" ) ) && !u.worn_with_flag( "FIX_FARSIGHT" ) &&
4525 !u.has_effect( effect_contacts ) && !u.has_bionic( bionic_id( "bio_eye_optic" ) ) ) {
4526 add_msg( m_info, _( "You'll need to put on reading glasses before you can see the screen." ) );
4527 return;
4528 }
4529
4530 computer *used = m.computer_at( p );
4531
4532 if( used == nullptr ) {
4533 if( m.has_flag( "CONSOLE", p ) ) { //Console without map data
4534 add_msg( m_bad, _( "The console doesn't display anything coherent." ) );
4535 } else {
4536 debugmsg( "Tried to use computer at %s - none there", p.to_string() );
4537 }
4538 return;
4539 }
4540
4541 computer_session( *used ).use();
4542}
void use()
Handles player use of a computer.
computer * computer_at(const tripoint &p)
Definition: map.cpp:5682
static const efftype_id effect_contacts("contacts")

References _, add_msg(), map::computer_at(), debugmsg, effect_contacts, Character::has_bionic(), Creature::has_effect(), map::has_flag(), Character::has_trait(), Character::is_blind(), m, m_bad, m_info, tripoint::to_string(), u, computer_session::use(), and Character::worn_with_flag().

Referenced by examine().

◆ validate_camps()

void game::validate_camps ( )

validate camps to ensure they are on the overmap list

Definition at line 1953 of file game.cpp.

1954{
1955 basecamp camp = m.hoist_submap_camp( u.pos() );
1956 if( camp.is_valid() ) {
1957 overmap_buffer.add_camp( camp );
1959 } else if( camp.camp_omt_pos() != tripoint_abs_omt() ) {
1960 std::string camp_name = _( "Faction Camp" );
1961 camp.set_name( camp_name );
1962 overmap_buffer.add_camp( camp );
1964 }
1965}
bool is_valid() const
Definition: basecamp.h:125
void set_name(const std::string &new_name)
Definition: basecamp.cpp:575
tripoint_abs_omt camp_omt_pos() const
Definition: basecamp.h:134
basecamp hoist_submap_camp(const tripoint &p)
Definition: map.cpp:5713
void remove_submap_camp(const tripoint &)
Definition: map.cpp:5708
void add_camp(const basecamp &camp)
Add Basecamp to overmapbuffer.

References _, overmapbuffer::add_camp(), basecamp::camp_omt_pos(), map::hoist_submap_camp(), basecamp::is_valid(), m, overmap_buffer, Character::pos(), map::remove_submap_camp(), basecamp::set_name(), and u.

Referenced by load().

◆ validate_linked_vehicles()

void game::validate_linked_vehicles ( )

validate towed vehicles so they get linked up again after a load

Definition at line 1895 of file game.cpp.

1896{
1897 for( auto &veh : m.get_vehicles() ) {
1898 vehicle *v = veh.v;
1901 if( other_v ) {
1902 // the other vehicle is towing us.
1903 v->tow_data.set_towing( other_v, v );
1905 }
1906 }
1907 }
1908}
tripoint other_towing_point
Definition: vehicle.h:166
bool set_towing(vehicle *tower_veh, vehicle *towed_veh)
Definition: vehicle.cpp:6140
towing_data tow_data
Definition: vehicle.h:1676

References map::get_vehicles(), m, towing_data::other_towing_point, towing_data::set_towing(), vehicle::tow_data, tripoint_zero, map::veh_at(), and veh_pointer_or_null().

Referenced by load().

◆ validate_mounted_npcs()

void game::validate_mounted_npcs ( )

Definition at line 1910 of file game.cpp.

1911{
1912 for( monster &m : all_monsters() ) {
1913 if( m.has_effect( effect_ridden ) && m.mounted_player_id.is_valid() ) {
1914 player *mounted_pl = g->critter_by_id<player>( m.mounted_player_id );
1915 if( !mounted_pl ) {
1916 // Target no longer valid.
1917 m.mounted_player_id = character_id();
1918 m.remove_effect( effect_ridden );
1919 continue;
1920 }
1921 mounted_pl->mounted_creature = shared_from( m );
1922 mounted_pl->setpos( m.pos() );
1923 mounted_pl->add_effect( effect_riding, 1_turns, num_bp );
1924 m.mounted_player = mounted_pl;
1925 }
1926 }
1927}

References Creature::add_effect(), all_monsters(), character_id, effect_ridden, effect_riding, g, m, Character::mounted_creature, num_bp, Character::setpos(), and shared_from().

Referenced by load(), and vertical_shift().

◆ validate_npc_followers()

void game::validate_npc_followers ( )

validate list of followers to account for overmap buffers

Definition at line 1929 of file game.cpp.

1930{
1931 // Make sure visible followers are in the list.
1932 const std::vector<npc *> visible_followers = get_npcs_if( [&]( const npc & guy ) {
1933 return guy.is_player_ally();
1934 } );
1935 for( npc *guy : visible_followers ) {
1936 update_faction_api( guy );
1937 add_npc_follower( guy->getID() );
1938 }
1939 // Make sure overmapbuffered NPC followers are in the list.
1940 for( const auto &temp_guy : overmap_buffer.get_npcs_near_player( 300 ) ) {
1941 npc *guy = temp_guy.get();
1942 if( guy->is_player_ally() ) {
1943 update_faction_api( guy );
1944 add_npc_follower( guy->getID() );
1945 }
1946 }
1947 // Make sure that serialized player followers sync up with game list
1948 for( const auto &temp_id : u.follower_ids ) {
1949 add_npc_follower( temp_id );
1950 }
1951}
void add_npc_follower(const character_id &id)
Add follower id to set of followers.
Definition: game.cpp:1875
static void update_faction_api(npc *guy)
Definition: game.cpp:1887

References add_npc_follower(), player::follower_ids, get_npcs_if(), overmapbuffer::get_npcs_near_player(), Character::getID(), npc::is_player_ally(), overmap_buffer, u, and update_faction_api().

Referenced by load().

◆ vertical_move()

void game::vertical_move ( int  z,
bool  force,
bool  peeking = false 
)

Moves the player vertically.

If force == true then they are falling. If peeking == true, forbids some exotic movement options

Strength increases breath-holding capacity while diving Dexterity increases chance of moving past monsters on stairs Dodge increases chance of moving past monsters on stairs Strength increases chance of moving past monsters on stairs Melee increases chance of moving past monsters on stairs

Definition at line 10015 of file game.cpp.

10016{
10017 if( u.is_mounted() ) {
10018 auto mons = u.mounted_creature.get();
10019 if( mons->has_flag( MF_RIDEABLE_MECH ) ) {
10020 if( !mons->check_mech_powered() ) {
10021 add_msg( m_bad, _( "Your %s refuses to move as its batteries have been drained." ),
10022 mons->get_name() );
10023 return;
10024 }
10025 }
10026 }
10027
10028 // > and < are used for diving underwater.
10029 if( m.has_flag( "SWIMMABLE", u.pos() ) && m.has_flag( TFLAG_DEEP_WATER, u.pos() ) ) {
10030 if( movez == -1 ) {
10031 if( u.is_underwater() ) {
10032 add_msg( m_info, _( "You are already underwater!" ) );
10033 return;
10034 }
10035 if( u.worn_with_flag( "FLOTATION" ) ) {
10036 add_msg( m_info, _( "You can't dive while wearing a flotation device." ) );
10037 return;
10038 }
10039 u.set_underwater( true );
10040 ///\EFFECT_STR increases breath-holding capacity while diving
10041 u.oxygen = 30 + 2 * u.str_cur;
10042 add_msg( _( "You dive underwater!" ) );
10043 } else {
10044 if( u.swim_speed() < 500 || u.shoe_type_count( itype_swim_fins ) ) {
10045 u.set_underwater( false );
10046 add_msg( _( "You surface." ) );
10047 } else {
10048 add_msg( m_info, _( "You try to surface but can't!" ) );
10049 }
10050 }
10051 u.moves -= 100;
10052 return;
10053 }
10054
10055 // Force means we're going down, even if there's no staircase, etc.
10056 bool climbing = false;
10057 int move_cost = 100;
10058 tripoint stairs( u.posx(), u.posy(), u.posz() + movez );
10059 if( m.has_zlevels() && !force && movez == 1 && !m.has_flag( "GOES_UP", u.pos() ) ) {
10060 // Climbing
10061 if( m.has_floor_or_support( stairs ) ) {
10062 add_msg( m_info, _( "You can't climb here - there's a ceiling above your head." ) );
10063 return;
10064 }
10065
10066 std::vector<tripoint> pts;
10067 for( const auto &pt : m.points_in_radius( stairs, 1 ) ) {
10068 if( m.passable( pt ) &&
10069 m.has_floor_or_support( pt ) ) {
10070 pts.push_back( pt );
10071 }
10072 }
10073
10074
10075 const auto cost = map_funcs::climbing_cost( m, u.pos(), stairs );
10076
10077 if( !cost.has_value() ) {
10078 if( u.has_trait( trait_WEB_ROPE ) ) {
10079 if( pts.empty() ) {
10080 add_msg( m_info, _( "There is nothing above you that you can attach a web to." ) );
10081 } else if( can_use_mutation_warn( trait_WEB_ROPE, u ) ) {
10082 if( m.move_cost( u.pos() ) != 2 && m.move_cost( u.pos() ) != 3 ) {
10083 add_msg( m_info, _( "You can't spin a web rope there." ) );
10084 } else if( m.has_furn( u.pos() ) ) {
10085 add_msg( m_info, _( "There is already furniture at that location." ) );
10086 } else {
10087 if( query_yn( "Spin a rope and climb?" ) ) {
10088 add_msg( m_good, _( "You spin a rope of web." ) );
10089 m.furn_set( u.pos(), furn_str_id( "f_rope_up_web" ) );
10090 u.mod_moves( to_turns<int>( 2_seconds ) );
10092 vertical_move( movez, force, peeking );
10093 }
10094 }
10095 }
10096
10097 } else {
10098 add_msg( m_info, _( "You can't climb here - you need walls and/or furniture to brace against." ) );
10099
10100 }
10101 return;
10102
10103 }
10104
10105 if( pts.empty() ) {
10106 add_msg( m_info,
10107 _( "You can't climb here - there is no terrain above you that would support your weight." ) );
10108 return;
10109 } else {
10110 // TODO: Make it an extended action
10111 climbing = true;
10112 move_cost = cost.value();
10113
10114 const std::optional<tripoint> pnt = point_selection_menu( pts );
10115 if( !pnt ) {
10116 return;
10117 }
10118 stairs = *pnt;
10119 }
10120 }
10121
10122 if( !force && movez == -1 && !m.has_flag( "GOES_DOWN", u.pos() ) ) {
10123 add_msg( m_info, _( "You can't go down here!" ) );
10124 return;
10125 } else if( !climbing && !force && movez == 1 && !m.has_flag( "GOES_UP", u.pos() ) ) {
10126 add_msg( m_info, _( "You can't go up here!" ) );
10127 return;
10128 }
10129
10130 if( force ) {
10131 // Let go of a grabbed cart.
10132 u.grab( OBJECT_NONE );
10133 } else if( u.grab_point != tripoint_zero ) {
10134 add_msg( m_info, _( "You can't drag things up and down stairs." ) );
10135 return;
10136 }
10137
10138 // Because get_levz takes z-value from the map, it will change when vertical_shift (m.has_zlevels() == true)
10139 // is called or when the map is loaded on new z-level (== false).
10140 // This caches the z-level we start the movement on (current) and the level we're want to end.
10141 const int z_before = get_levz();
10142 const int z_after = get_levz() + movez;
10143 if( z_after < -OVERMAP_DEPTH || z_after > OVERMAP_HEIGHT ) {
10144 debugmsg( "Tried to move outside allowed range of z-levels" );
10145 return;
10146 }
10147
10148 if( !u.move_effects( false ) ) {
10149 return;
10150 }
10151
10152 // Check if there are monsters are using the stairs.
10153 bool slippedpast = false;
10154 if( !m.has_zlevels() && !coming_to_stairs.empty() && !force ) {
10155 // TODO: Allow travel if zombie couldn't reach stairs, but spawn him when we go up.
10156 add_msg( m_warning, _( "You try to use the stairs. Suddenly you are blocked by a %s!" ),
10157 coming_to_stairs[0].name() );
10158 // Roll.
10159 ///\EFFECT_DEX increases chance of moving past monsters on stairs
10160
10161 ///\EFFECT_DODGE increases chance of moving past monsters on stairs
10162 int dexroll = dice( 6, u.dex_cur + u.get_skill_level( skill_dodge ) * 2 );
10163 ///\EFFECT_STR increases chance of moving past monsters on stairs
10164
10165 ///\EFFECT_MELEE increases chance of moving past monsters on stairs
10166 int strroll = dice( 3, u.str_cur + u.get_skill_level( skill_melee ) * 1.5 );
10167 if( coming_to_stairs.size() > 4 ) {
10168 add_msg( _( "The are a lot of them on the %s!" ), m.tername( u.pos() ) );
10169 dexroll /= 4;
10170 strroll /= 2;
10171 } else if( coming_to_stairs.size() > 1 ) {
10172 add_msg( m_warning, _( "There's something else behind it!" ) );
10173 dexroll /= 2;
10174 }
10175
10176 if( dexroll < 14 || strroll < 12 ) {
10178 u.moves -= 100;
10179 return;
10180 }
10181
10182 add_msg( _( "You manage to slip past!" ) );
10183 slippedpast = true;
10184 u.moves -= 100;
10185 }
10186
10187 // Shift the map up or down
10188
10189 std::unique_ptr<map> tmp_map_ptr;
10190 if( !m.has_zlevels() ) {
10191 tmp_map_ptr = std::make_unique<map>();
10192 }
10193
10194 map &maybetmp = m.has_zlevels() ? m : *( tmp_map_ptr.get() );
10195 if( m.has_zlevels() ) {
10196 // We no longer need to shift the map here! What joy
10197 } else {
10198 maybetmp.load( tripoint( get_levx(), get_levy(), z_after ), false );
10199 }
10200
10201 // Find the corresponding staircase
10202 bool rope_ladder = false;
10203 // TODO: Remove the stairfinding, make the mapgen gen aligned maps
10204 if( !force && !climbing ) {
10205 const std::optional<tripoint> pnt = find_or_make_stairs( maybetmp, z_after, rope_ladder, peeking );
10206 if( !pnt ) {
10207 return;
10208 }
10209 stairs = *pnt;
10210 }
10211
10212 if( !force ) {
10213 monstairz = z_before;
10214 }
10215 // Save all monsters that can reach the stairs, remove them from the tracker,
10216 // then despawn the remaining monsters. Because it's a vertical shift, all
10217 // monsters are out of the bounds of the map and will despawn.
10218 shared_ptr_fast<monster> stored_mount;
10219 if( u.is_mounted() && !m.has_zlevels() ) {
10220 // Store a *copy* of the mount, so we can remove the original monster instance
10221 // from the tracker before the map shifts.
10222 // Map shifting would otherwise just despawn the mount and would later respawn it.
10223 stored_mount = make_shared_fast<monster>( *u.mounted_creature );
10225 }
10226 if( !m.has_zlevels() ) {
10227 const tripoint to = u.pos();
10228 for( monster &critter : all_monsters() ) {
10229 // if its a ladder instead of stairs - most zombies can't climb that.
10230 // unless that have a special flag to allow them to do so.
10231 if( ( m.has_flag( "DIFFICULT_Z", u.pos() ) && !critter.climbs() ) ||
10232 critter.has_effect( effect_ridden ) ||
10233 critter.has_effect( effect_tied ) ) {
10234 continue;
10235 }
10236 int turns = critter.turns_to_reach( to.xy() );
10237 if( turns < 10 && coming_to_stairs.size() < 8 && critter.will_reach( to.xy() )
10238 && !slippedpast ) {
10239 critter.staircount = 10 + turns;
10240 critter.on_unload();
10241 coming_to_stairs.push_back( critter );
10242 remove_zombie( critter );
10243 }
10244 }
10245 auto mons = critter_tracker->find( g->u.pos() );
10246 if( mons != nullptr ) {
10247 critter_tracker->remove( *mons );
10248 }
10249 shift_monsters( tripoint( 0, 0, movez ) );
10250 }
10251
10252 std::vector<shared_ptr_fast<npc>> npcs_to_bring;
10253 std::vector<monster *> monsters_following;
10254 if( !m.has_zlevels() && std::abs( movez ) == 1 ) {
10255 std::copy_if( active_npc.begin(), active_npc.end(), back_inserter( npcs_to_bring ),
10256 [this]( const shared_ptr_fast<npc> &np ) {
10257 return np->is_walking_with() && !np->is_mounted() && !np->in_sleep_state() &&
10258 rl_dist( np->pos(), u.pos() ) < 2;
10259 } );
10260 }
10261
10262 if( m.has_zlevels() && std::abs( movez ) == 1 ) {
10263 bool ladder = m.has_flag( "DIFFICULT_Z", u.pos() );
10264 for( monster &critter : all_monsters() ) {
10265 if( ladder && !critter.climbs() ) {
10266 continue;
10267 }
10268 if( critter.attack_target() == &g->u || ( !critter.has_effect( effect_ridden ) &&
10269 critter.has_effect( effect_pet ) && critter.friendly == -1 &&
10270 !critter.has_effect( effect_tied ) ) ) {
10271 monsters_following.push_back( &critter );
10272 }
10273 }
10274 }
10275
10276 if( u.is_mounted() ) {
10277 monster *crit = u.mounted_creature.get();
10278 if( crit->has_flag( MF_RIDEABLE_MECH ) ) {
10279 crit->use_mech_power( -1 );
10280 if( u.movement_mode_is( CMM_WALK ) ) {
10281 crit->use_mech_power( -2 );
10282 } else if( u.movement_mode_is( CMM_CROUCH ) ) {
10283 crit->use_mech_power( -1 );
10284 } else if( u.movement_mode_is( CMM_RUN ) ) {
10285 crit->use_mech_power( -3 );
10286 }
10287 }
10288 } else {
10289 u.moves -= move_cost;
10290 }
10291 for( const auto &np : npcs_to_bring ) {
10292 if( np->in_vehicle ) {
10293 m.unboard_vehicle( np->pos() );
10294 }
10295 }
10296 const tripoint old_pos = g->u.pos();
10297 point submap_shift;
10298 vertical_shift( z_after );
10299 if( !force ) {
10300 submap_shift = update_map( stairs.x, stairs.y );
10301 }
10302
10303 // if an NPC or monster is on the stiars when player ascends/descends
10304 // they may end up merged on th esame tile, do some displacement to resolve that.
10305 // if, in the weird case of it not being possible to displace;
10306 // ( how did the player even manage to approach the stairs, if so? )
10307 // then nothing terrible happens, its just weird.
10308 if( critter_at<npc>( u.pos(), true ) || critter_at<monster>( u.pos(), true ) ) {
10309 std::string crit_name;
10310 bool player_displace = false;
10311 std::optional<tripoint> displace = find_empty_spot_nearby( u.pos() );
10312 if( displace.has_value() ) {
10313 npc *guy = g->critter_at<npc>( u.pos(), true );
10314 if( guy ) {
10315 crit_name = guy->get_name();
10316 tripoint old_pos = guy->pos();
10317 if( !guy->is_enemy() ) {
10318 guy->move_away_from( u.pos(), true );
10319 if( old_pos != guy->pos() ) {
10320 add_msg( _( "%s moves out of the way for you." ), guy->get_name() );
10321 }
10322 } else {
10323 player_displace = true;
10324 }
10325 }
10326 monster *mon = g->critter_at<monster>( u.pos(), true );
10327 // if the monster is ridden by the player or an NPC:
10328 // Dont displace them. If they are mounted by a friendly NPC,
10329 // then the NPC will already have been displaced just above.
10330 // if they are ridden by the player, we want them to coexist on same tile
10331 if( mon && !mon->mounted_player ) {
10332 crit_name = mon->get_name();
10333 if( mon->friendly == -1 ) {
10334 mon->setpos( *displace );
10335 add_msg( _( "Your %s moves out of the way for you." ), mon->get_name() );
10336 } else {
10337 player_displace = true;
10338 }
10339 }
10340 if( player_displace ) {
10341 u.setpos( *displace );
10342 u.moves -= 20;
10343 add_msg( _( "You push past %s blocking the way." ), crit_name );
10344 }
10345 } else {
10346 debugmsg( "Failed to find a spot to displace into." );
10347 }
10348 }
10349
10350 // Now that we know the player's destination position, we can move their mount as well
10351 if( u.is_mounted() ) {
10352 if( stored_mount ) {
10353 assert( !m.has_zlevels() );
10354 stored_mount->spawn( g->u.pos() );
10355 if( critter_tracker->add( stored_mount ) ) {
10356 u.mounted_creature = stored_mount;
10357 }
10358 } else {
10359 u.mounted_creature->setpos( g->u.pos() );
10360 }
10361 }
10362
10363 if( !npcs_to_bring.empty() ) {
10364 // Would look nicer randomly scrambled
10365 std::vector<tripoint> candidates = closest_points_first( u.pos(), 1 );
10366 candidates.erase( std::remove_if( candidates.begin(), candidates.end(),
10367 [this]( const tripoint & c ) {
10368 return !is_empty( c );
10369 } ), candidates.end() );
10370
10371 for( const auto &np : npcs_to_bring ) {
10372 const auto found = std::find_if( candidates.begin(), candidates.end(),
10373 [this, np]( const tripoint & c ) {
10374 return !np->is_dangerous_fields( m.field_at( c ) ) && m.tr_at( c ).is_benign();
10375 } );
10376 if( found != candidates.end() ) {
10377 // TODO: De-uglify
10378 np->setpos( *found );
10379 np->place_on_map();
10380 np->setpos( *found );
10381 candidates.erase( found );
10382 }
10383
10384 if( candidates.empty() ) {
10385 break;
10386 }
10387 }
10388
10389 reload_npcs();
10390 }
10391
10392 // This ugly check is here because of stair teleport bullshit
10393 // TODO: Remove stair teleport bullshit
10394 if( rl_dist( g->u.pos(), old_pos ) <= 1 ) {
10395 for( monster *m : monsters_following ) {
10396 m->set_dest( g->u.pos() );
10397 }
10398 }
10399
10400 if( rope_ladder ) {
10401 m.ter_set( u.pos(), t_rope_up );
10402 }
10403
10404 if( m.ter( stairs ) == t_manhole_cover ) {
10405 m.spawn_item( stairs + point( rng( -1, 1 ), rng( -1, 1 ) ), itype_manhole_cover );
10406 m.ter_set( stairs, t_manhole );
10407 }
10408
10409 // Wouldn't work and may do strange things
10410 if( u.is_hauling() && !m.has_zlevels() ) {
10411 add_msg( _( "You cannot haul items here." ) );
10412 u.stop_hauling();
10413 }
10414
10415 if( u.is_hauling() ) {
10416 const tripoint adjusted_pos = old_pos - sm_to_ms_copy( submap_shift );
10417 start_hauling( adjusted_pos );
10418 }
10419
10420 m.invalidate_map_cache( g->get_levz() );
10421 // Upon force movement, traps can not be avoided.
10422 m.creature_on_trap( u, !force );
10423
10425}
static int move_cost(const item &it, const tripoint &src, const tripoint &dest)
@ CMM_WALK
Definition: character.h:109
@ CMM_CROUCH
Definition: character.h:111
bool move_effects(bool attacking) override
Processes effects which may prevent the Character from moving (bear traps, crushed,...
Definition: character.cpp:1476
int swim_speed() const
Returns the player's speed for swimming across water tiles.
Definition: character.cpp:818
int oxygen
Definition: character.h:1593
void mutation_spend_resources(const trait_id &mut)
Removes the appropriate costs (NOTE: will reapply mods & recalc sightlines in case of newly activated...
Definition: mutation.cpp:1698
int shoe_type_count(const itype_id &it) const
Returns 1 if the player is wearing an item of that count on one foot, 2 if on both,...
Definition: character.cpp:8950
std::string get_name() const override
Definition: character.cpp:5998
void set_underwater(bool x) override
void start_hauling(const tripoint &pos)
Definition: game.cpp:10427
std::optional< tripoint > find_or_make_stairs(map &mp, int z_after, bool &rope_ladder, bool peeking)
Returns the other end of the stairs (if any).
Definition: game.cpp:10462
bool use_mech_power(int amt)
Definition: monster.cpp:2441
Character * mounted_player
Definition: monster.h:458
static const efftype_id effect_tied("tied")
static const itype_id itype_manhole_cover("manhole_cover")
static std::optional< tripoint > point_selection_menu(const std::vector< tripoint > &pts)
Definition: game.cpp:9965
static const skill_id skill_melee("melee")
static const itype_id itype_swim_fins("swim_fins")
static const trait_id trait_WEB_ROPE("WEB_ROPE")
ter_id t_rope_up
Definition: mapdata.cpp:722
ter_id t_manhole
Definition: mapdata.cpp:721
bool can_use_mutation_warn(const trait_id &mut, const Character &character)
Calls can_use_mutation and if it fails, print a standard message.
Definition: mutation.cpp:1687
void avatar_moves(const avatar &u, const map &m, const tripoint &p)
Definition: game.cpp:12101
int ladder(player *, item *, bool, const tripoint &)
Definition: iuse.cpp:9325
auto climbing_cost(const map &m, const tripoint &from, const tripoint &to) -> std::optional< int >
Checks both the neighborhoods of from and to for climbable surfaces, returns move cost of climbing fr...
point displace(type dir, int dist=1)
Returns point(0, 0) displaced in specified direction by a specified distance.
Definition: overmap.cpp:4191

References _, active_npc, add_msg(), all_monsters(), cata_event_dispatch::avatar_moves(), c, can_use_mutation_warn(), map_funcs::climbing_cost(), closest_points_first(), CMM_CROUCH, CMM_RUN, CMM_WALK, coming_to_stairs, map::creature_on_trap(), critter_tracker, debugmsg, Character::dex_cur, dice(), om_direction::displace(), effect_pet, effect_ridden, effect_tied, find_empty_spot_nearby(), find_or_make_stairs(), monster::friendly, map::furn_set(), g, get_levx(), get_levy(), get_levz(), Character::get_name(), monster::get_name(), Character::get_skill_level(), avatar::grab(), player::grab_point, map::has_flag(), monster::has_flag(), map::has_floor_or_support(), map::has_furn(), Character::has_trait(), map::has_zlevels(), map::invalidate_map_cache(), npc::is_enemy(), Character::is_hauling(), Character::is_mounted(), Creature::is_underwater(), itype_manhole_cover, itype_swim_fins, iuse::ladder(), map::load(), m, m_bad, m_good, m_info, m_warning, MF_RIDEABLE_MECH, Creature::mod_moves(), monstairz, Character::mounted_creature, monster::mounted_player, npc::move_away_from(), move_cost(), map::move_cost(), Character::move_effects(), Character::movement_mode_is(), Creature::moves, Character::mutation_spend_resources(), om_direction::name(), OBJECT_NONE, OVERMAP_HEIGHT, Character::oxygen, map::passable(), point_selection_menu(), map::points_in_radius(), Character::pos(), Character::posx(), Character::posy(), Character::posz(), query_yn(), reload_npcs(), remove_zombie(), rl_dist(), rng(), Character::set_underwater(), Character::setpos(), monster::setpos(), shift_monsters(), Character::shoe_type_count(), skill_dodge, skill_melee, sm_to_ms_copy(), map::spawn_item(), start_hauling(), Character::stop_hauling(), Character::str_cur, Character::swim_speed(), t_manhole, t_manhole_cover, t_rope_up, map::ter(), map::ter_set(), map::tername(), TFLAG_DEEP_WATER, trait_WEB_ROPE, tripoint_zero, u, map::unboard_vehicle(), update_map(), update_stair_monsters(), monster::use_mech_power(), vertical_move(), vertical_shift(), Character::worn_with_flag(), tripoint::x, tripoint::xy(), and tripoint::y.

Referenced by handle_action(), peek(), and vertical_move().

◆ vertical_notes()

void game::vertical_notes ( int  z_before,
int  z_after 
)

Add goes up/down auto_notes (if turned on)

Definition at line 10649 of file game.cpp.

10650{
10651 if( z_before == z_after || !get_option<bool>( "AUTO_NOTES" ) ||
10652 !get_option<bool>( "AUTO_NOTES_STAIRS" ) ) {
10653 return;
10654 }
10655
10656 if( !m.inbounds_z( z_before ) || !m.inbounds_z( z_after ) ) {
10657 debugmsg( "game::vertical_notes invalid arguments: z_before == %d, z_after == %d",
10658 z_before, z_after );
10659 return;
10660 }
10661 // Figure out where we know there are up/down connectors
10662 // Fill in all the tiles we know about (e.g. subway stations)
10663 static const int REVEAL_RADIUS = 40;
10664 for( const tripoint_abs_omt &p : points_in_radius( u.global_omt_location(), REVEAL_RADIUS ) ) {
10665 const tripoint_abs_omt cursp_before( p.xy(), z_before );
10666 const tripoint_abs_omt cursp_after( p.xy(), z_after );
10667
10668 if( !overmap_buffer.seen( cursp_before ) ) {
10669 continue;
10670 }
10671 if( overmap_buffer.has_note( cursp_after ) ) {
10672 // Already has a note -> never add an AUTO-note
10673 continue;
10674 }
10675 const oter_id &ter = overmap_buffer.ter( cursp_before );
10676 const oter_id &ter2 = overmap_buffer.ter( cursp_after );
10677 if( z_after > z_before && ter->has_flag( known_up ) &&
10678 !ter2->has_flag( known_down ) ) {
10679 overmap_buffer.set_seen( cursp_after, true );
10680 overmap_buffer.add_note( cursp_after, string_format( ">:W;%s", _( "AUTO: goes down" ) ) );
10681 } else if( z_after < z_before && ter->has_flag( known_down ) &&
10682 !ter2->has_flag( known_up ) ) {
10683 overmap_buffer.set_seen( cursp_after, true );
10684 overmap_buffer.add_note( cursp_after, string_format( "<:W;%s", _( "AUTO: goes up" ) ) );
10685 }
10686 }
10687}
bool inbounds_z(const int z) const
Definition: map.h:1628
void add_note(const tripoint_abs_omt &, const std::string &message)
@ known_up
Definition: omdata.h:87
@ known_down
Definition: omdata.h:86
bool has_flag(oter_flags flag) const
Definition: omdata.h:258

References _, overmapbuffer::add_note(), debugmsg, Character::global_omt_location(), oter_t::has_flag(), overmapbuffer::has_note(), map::inbounds_z(), known_down, known_up, m, overmap_buffer, points_in_radius(), overmapbuffer::seen(), overmapbuffer::set_seen(), string_format(), overmapbuffer::ter(), and u.

Referenced by vertical_shift().

◆ vertical_shift()

void game::vertical_shift ( int  z_after)

Actual z-level movement part of vertical_move.

Doesn't include stair finding, traps etc.

Definition at line 10612 of file game.cpp.

10613{
10614 if( z_after < -OVERMAP_DEPTH || z_after > OVERMAP_HEIGHT ) {
10615 debugmsg( "Tried to get z-level %d outside allowed range of %d-%d",
10616 z_after, -OVERMAP_DEPTH, OVERMAP_HEIGHT );
10617 return;
10618 }
10619
10620 // TODO: Implement dragging stuff up/down
10621 u.grab( OBJECT_NONE );
10622
10623 scent.reset();
10624
10625 u.setz( z_after );
10626 const int z_before = get_levz();
10627 if( !m.has_zlevels() ) {
10629 m.access_cache( z_before ).vehicle_list.clear();
10630 m.access_cache( z_before ).zone_vehicles.clear();
10631 m.access_cache( z_before ).map_memory_seen_cache.reset();
10632 m.set_transparency_cache_dirty( z_before );
10633 m.set_outside_cache_dirty( z_before );
10634 m.load( tripoint( get_levx(), get_levy(), z_after ), true );
10635 shift_monsters( tripoint( 0, 0, z_after - z_before ) );
10636 reload_npcs();
10637 } else {
10638 // Shift the map itself
10639 m.vertical_shift( z_after );
10640 }
10641
10642 m.spawn_monsters( true );
10643 // this may be required after a vertical shift if z-levels are not enabled
10644 // the critter is unloaded/loaded, and it needs to reconstruct its rider data after being reloaded.
10646 vertical_notes( z_before, z_after );
10647}
void setz(int z)
Definition: character.h:812
void vertical_notes(int z_before, int z_after)
Add goes up/down auto_notes (if turned on)
Definition: game.cpp:10649
void set_transparency_cache_dirty(const int zlev)
Sets a dirty flag on the a given cache.
Definition: map.cpp:201
void set_outside_cache_dirty(const int zlev)
Definition: map.cpp:222
void vertical_shift(int newz)
Moves the map vertically to (not by!) newz.
Definition: map.cpp:7050
std::set< vehicle * > zone_vehicles
Definition: map.h:358
std::set< vehicle * > vehicle_list
Definition: map.h:357

References map::access_cache(), map::clear_vehicle_cache(), debugmsg, get_levx(), get_levy(), get_levz(), avatar::grab(), map::has_zlevels(), map::load(), m, level_cache::map_memory_seen_cache, OBJECT_NONE, OVERMAP_DEPTH, OVERMAP_HEIGHT, reload_npcs(), scent_map::reset(), scent, map::set_outside_cache_dirty(), map::set_transparency_cache_dirty(), Character::setz(), shift_monsters(), map::spawn_monsters(), u, validate_mounted_npcs(), level_cache::vehicle_list, vertical_notes(), map::vertical_shift(), and level_cache::zone_vehicles.

Referenced by place_player(), and vertical_move().

◆ walk_move()

bool game::walk_move ( const tripoint dest,
bool  via_ramp = false 
)

TODO: This should really use the mounted creatures stamina, if mounted. Monsters don't currently have stamina however. For the time being just don't burn players stamina when mounted.

Dexterity decreases chance of tentacles getting stuck to the ground Intelligence decreases chance of tentacles getting stuck to the ground

Definition at line 8797 of file game.cpp.

8798{
8799 if( m.has_flag_ter( TFLAG_SMALL_PASSAGE, dest_loc ) ) {
8800 if( u.get_size() > MS_MEDIUM ) {
8801 add_msg( m_warning, _( "You can't fit there." ) );
8802 return false; // character too large to fit through a tight passage
8803 }
8804 if( u.is_mounted() ) {
8805 monster *mount = u.mounted_creature.get();
8806 if( mount->get_size() > MS_MEDIUM ) {
8807 add_msg( m_warning, _( "Your mount can't fit there." ) );
8808 return false; // char's mount is too large for tight passages
8809 }
8810 }
8811 }
8812
8813 if( u.is_mounted() ) {
8814 auto mons = u.mounted_creature.get();
8815 if( mons->has_flag( MF_RIDEABLE_MECH ) ) {
8816 if( !mons->check_mech_powered() ) {
8817 add_msg( m_bad, _( "Your %s refuses to move as its batteries have been drained." ),
8818 mons->get_name() );
8819 return false;
8820 }
8821 }
8822 if( !mons->move_effects( false ) ) {
8823 add_msg( m_bad, _( "You cannot move as your %s isn't able to move." ), mons->get_name() );
8824 return false;
8825 }
8826 }
8827 const optional_vpart_position vp_here = m.veh_at( u.pos() );
8828 const optional_vpart_position vp_there = m.veh_at( dest_loc );
8829
8830 bool pushing = false; // moving -into- grabbed tile; skip check for move_cost > 0
8831 bool pulling = false; // moving -away- from grabbed tile; check for move_cost > 0
8832 bool shifting_furniture = false; // moving furniture and staying still; skip check for move_cost > 0
8833
8834 const tripoint furn_pos = u.pos() + u.grab_point;
8835 const tripoint furn_dest = dest_loc + u.grab_point;
8836
8837 bool grabbed = u.get_grab_type() != OBJECT_NONE;
8838 if( grabbed ) {
8839 const tripoint dp = dest_loc - u.pos();
8840 pushing = dp == u.grab_point;
8841 pulling = dp == -u.grab_point;
8842 }
8843 if( grabbed && dest_loc.z != u.posz() ) {
8844 add_msg( m_warning, _( "You let go of the grabbed object." ) );
8845 grabbed = false;
8846 u.grab( OBJECT_NONE );
8847 }
8848
8849 // Now make sure we're actually holding something
8850 const vehicle *grabbed_vehicle = nullptr;
8851 if( grabbed && u.get_grab_type() == OBJECT_FURNITURE ) {
8852 // We only care about shifting, because it's the only one that can change our destination
8853 if( m.has_furn( u.pos() + u.grab_point ) ) {
8854 shifting_furniture = !pushing && !pulling;
8855 } else {
8856 // We were grabbing a furniture that isn't there
8857 grabbed = false;
8858 }
8859 } else if( grabbed && u.get_grab_type() == OBJECT_VEHICLE ) {
8860 grabbed_vehicle = veh_pointer_or_null( m.veh_at( u.pos() + u.grab_point ) );
8861 if( grabbed_vehicle == nullptr ) {
8862 // We were grabbing a vehicle that isn't there anymore
8863 grabbed = false;
8864 }
8865 } else if( grabbed ) {
8866 // We were grabbing something WEIRD, let's pretend we weren't
8867 grabbed = false;
8868 }
8869 if( u.grab_point != tripoint_zero && !grabbed ) {
8870 add_msg( m_warning, _( "Can't find grabbed object." ) );
8871 u.grab( OBJECT_NONE );
8872 }
8873
8874 if( m.impassable( dest_loc ) && !pushing && !shifting_furniture ) {
8875 if( vp_there && u.mounted_creature && u.mounted_creature->has_flag( MF_RIDEABLE_MECH ) &&
8876 vp_there->vehicle().handle_potential_theft( u ) ) {
8877 tripoint diff = dest_loc - u.pos();
8878 if( diff.x < 0 ) {
8879 diff.x -= 2;
8880 } else if( diff.x > 0 ) {
8881 diff.x += 2;
8882 }
8883 if( diff.y < 0 ) {
8884 diff.y -= 2;
8885 } else if( diff.y > 0 ) {
8886 diff.y += 2;
8887 }
8888 u.mounted_creature->shove_vehicle( dest_loc + diff.xy(),
8889 dest_loc );
8890 }
8891 return false;
8892 }
8893 if( vp_there && !vp_there->vehicle().handle_potential_theft( u ) ) {
8894 return false;
8895 }
8896 if( u.is_mounted() && !pushing && vp_there ) {
8897 add_msg( m_warning, _( "You cannot board a vehicle whilst riding." ) );
8898 return false;
8899 }
8900 u.set_underwater( false );
8901
8902 if( !shifting_furniture && !pushing && is_dangerous_tile( dest_loc ) ) {
8903 std::vector<std::string> harmful_stuff = get_dangerous_tile( dest_loc );
8904 const auto dangerous_terrain_opt = get_option<std::string>( "DANGEROUS_TERRAIN_WARNING_PROMPT" );
8905 const auto harmful_text = enumerate_as_string( harmful_stuff );
8906 const auto looks_risky = _( "Stepping into that %1$s looks risky. %2$s" );
8907
8908 const auto warn_msg = [&]( std::string_view action ) {
8909 add_msg( m_warning, looks_risky, harmful_text, action.data() );
8910 };
8911
8912 if( dangerous_terrain_opt == "IGNORE" ) {
8913 warn_msg( _( "But you enter anyway." ) );
8914 } else if( dangerous_terrain_opt == "ALWAYS" && !prompt_dangerous_tile( dest_loc ) ) {
8915 return true;
8916 } else if( dangerous_terrain_opt == "RUNNING" &&
8917 ( !u.movement_mode_is( CMM_RUN ) || !prompt_dangerous_tile( dest_loc ) ) ) {
8918 warn_msg( _( "Run into it if you wish to enter anyway." ) );
8919 return true;
8920 } else if( dangerous_terrain_opt == "CROUCHING" &&
8921 ( !u.movement_mode_is( CMM_CROUCH ) || !prompt_dangerous_tile( dest_loc ) ) ) {
8922 warn_msg( _( "Crouch and move into it if you wish to enter anyway." ) );
8923 return true;
8924 } else if( dangerous_terrain_opt == "NEVER" && !u.movement_mode_is( CMM_RUN ) ) {
8925 warn_msg( _( "Run into it if you wish to enter anyway." ) );
8926 return true;
8927 }
8928 }
8929 // Used to decide whether to print a 'moving is slow message
8930 const int mcost_from = m.move_cost( u.pos() ); //calculate this _before_ calling grabbed_move
8931
8932 int modifier = 0;
8933 if( grabbed && u.get_grab_type() == OBJECT_FURNITURE && u.pos() + u.grab_point == dest_loc ) {
8934 modifier = -m.furn( dest_loc ).obj().movecost;
8935 }
8936
8937 int multiplier = 1;
8938 if( u.is_on_ground() ) {
8939 multiplier *= 3;
8940 }
8941
8942 const int mcost = m.combined_movecost( u.pos(), dest_loc, grabbed_vehicle, modifier,
8943 via_ramp ) * multiplier;
8944 if( grabbed_move( dest_loc - u.pos() ) ) {
8945 return true;
8946 } else if( mcost == 0 ) {
8947 return false;
8948 }
8949 bool diag = trigdist && u.posx() != dest_loc.x && u.posy() != dest_loc.y;
8950 const int previous_moves = u.moves;
8951 if( u.is_mounted() ) {
8952 auto crit = u.mounted_creature.get();
8953 if( !crit->has_flag( MF_RIDEABLE_MECH ) &&
8954 ( m.has_flag_ter_or_furn( "MOUNTABLE", dest_loc ) ||
8955 m.has_flag_ter_or_furn( "BARRICADABLE_DOOR", dest_loc ) ||
8956 m.has_flag_ter_or_furn( "OPENCLOSE_INSIDE", dest_loc ) ||
8957 m.has_flag_ter_or_furn( "BARRICADABLE_DOOR_DAMAGED", dest_loc ) ||
8958 m.has_flag_ter_or_furn( "BARRICADABLE_DOOR_REINFORCED", dest_loc ) ) ) {
8959 add_msg( m_warning, _( "You cannot pass obstacles whilst mounted." ) );
8960 return false;
8961 }
8962 const double base_moves = u.run_cost( mcost, diag ) * 100.0 / crit->get_speed();
8963 const double encumb_moves = u.get_weight() / 4800.0_gram;
8964 u.moves -= static_cast<int>( std::ceil( base_moves + encumb_moves ) );
8965 if( u.movement_mode_is( CMM_WALK ) ) {
8966 crit->use_mech_power( -2 );
8967 } else if( u.movement_mode_is( CMM_CROUCH ) ) {
8968 crit->use_mech_power( -1 );
8969 } else if( u.movement_mode_is( CMM_RUN ) ) {
8970 crit->use_mech_power( -3 );
8971 }
8972 } else {
8973 u.moves -= u.run_cost( mcost, diag );
8974 /**
8975 TODO:
8976 This should really use the mounted creatures stamina, if mounted.
8977 Monsters don't currently have stamina however.
8978 For the time being just don't burn players stamina when mounted.
8979 */
8980 if( grabbed_vehicle == nullptr || grabbed_vehicle->wheelcache.empty() ) {
8981 //Burn normal amount of stamina if no vehicle grabbed or vehicle lacks wheels
8982 u.burn_move_stamina( previous_moves - u.moves );
8983 } else {
8984 //Burn half as much stamina if vehicle has wheels, without changing move time
8985 u.burn_move_stamina( 0.50 * ( previous_moves - u.moves ) );
8986 }
8987 }
8988 // Max out recoil & reset aim point
8990 u.last_target_pos = std::nullopt;
8991
8992 // Print a message if movement is slow
8993 const int mcost_to = m.move_cost( dest_loc ); //calculate this _after_ calling grabbed_move
8994 const bool fungus = m.has_flag_ter_or_furn( "FUNGUS", u.pos() ) ||
8995 m.has_flag_ter_or_furn( "FUNGUS",
8996 dest_loc ); //fungal furniture has no slowing effect on mycus characters
8997 const bool slowed = ( ( !u.has_trait( trait_PARKOUR ) && ( mcost_to > 2 || mcost_from > 2 ) ) ||
8998 mcost_to > 4 || mcost_from > 4 ) &&
8999 !( u.has_trait( trait_M_IMMUNE ) && fungus );
9000 if( slowed && !u.is_mounted() ) {
9001 // Unless u.pos() has a higher movecost than dest_loc, state that dest_loc is the cause
9002 if( mcost_to >= mcost_from ) {
9003 if( auto displayed_part = vp_there.part_displayed() ) {
9004 add_msg( m_warning, _( "Moving onto this %s is slow!" ),
9005 displayed_part->part().name() );
9006 sfx::do_obstacle( displayed_part->part().info().get_id().str() );
9007 } else {
9008 add_msg( m_warning, _( "Moving onto this %s is slow!" ), m.name( dest_loc ) );
9009 sfx::do_obstacle( m.ter( dest_loc ).id().str() );
9010 }
9011 } else {
9012 if( auto displayed_part = vp_here.part_displayed() ) {
9013 add_msg( m_warning, _( "Moving off of this %s is slow!" ),
9014 displayed_part->part().name() );
9015 sfx::do_obstacle( displayed_part->part().info().get_id().str() );
9016 } else {
9017 add_msg( m_warning, _( "Moving off of this %s is slow!" ), m.name( u.pos() ) );
9018 sfx::do_obstacle( m.ter( u.pos() ).id().str() );
9019 }
9020 }
9021 }
9022 if( !u.is_mounted() && u.has_trait( trait_id( "LEG_TENT_BRACE" ) ) &&
9023 ( !u.footwear_factor() ||
9024 ( u.footwear_factor() == .5 && one_in( 2 ) ) ) ) {
9025 // DX and IN are long suits for Cephalopods,
9026 // so this shouldn't cause too much hardship
9027 // Presumed that if it's swimmable, they're
9028 // swimming and won't stick
9029 ///\EFFECT_DEX decreases chance of tentacles getting stuck to the ground
9030
9031 ///\EFFECT_INT decreases chance of tentacles getting stuck to the ground
9032 if( !m.has_flag( "SWIMMABLE", dest_loc ) && one_in( 80 + u.dex_cur + u.int_cur ) ) {
9033 add_msg( _( "Your tentacles stick to the ground, but you pull them free." ) );
9034 u.mod_fatigue( 1 );
9035 }
9036 }
9037 if( !u.has_artifact_with( AEP_STEALTH ) && !u.has_trait( trait_id( "DEBUG_SILENT" ) ) ) {
9038 int volume = u.is_stealthy() ? 3 : 6;
9039 volume *= u.mutation_value( "noise_modifier" );
9040 if( volume > 0 ) {
9042 volume = 2;
9043 } else if( u.has_bionic( bionic_id( "bio_ankles" ) ) ) {
9044 volume = 12;
9045 }
9046 if( u.movement_mode_is( CMM_RUN ) ) {
9047 volume *= 1.5;
9048 } else if( u.movement_mode_is( CMM_CROUCH ) ) {
9049 volume /= 2;
9050 }
9051 if( u.is_mounted() ) {
9052 auto mons = u.mounted_creature.get();
9053 switch( mons->get_size() ) {
9054 case MS_TINY:
9055 volume = 0; // No sound for the tinies
9056 break;
9057 case MS_SMALL:
9058 volume /= 3;
9059 break;
9060 case MS_MEDIUM:
9061 break;
9062 case MS_LARGE:
9063 volume *= 1.5;
9064 break;
9065 case MS_HUGE:
9066 volume *= 2;
9067 break;
9068 default:
9069 break;
9070 }
9071 if( mons->has_flag( MF_LOUDMOVES ) ) {
9072 volume += 6;
9073 }
9074 sounds::sound( dest_loc, volume, sounds::sound_t::movement, mons->type->get_footsteps(), false,
9075 "none", "none" );
9076 } else {
9077 sounds::sound( dest_loc, volume, sounds::sound_t::movement, _( "footsteps" ), true,
9078 "none", "none" ); // Sound of footsteps may awaken nearby monsters
9079 }
9081 }
9082
9083 if( one_in( 20 ) && u.has_artifact_with( AEP_MOVEMENT_NOISE ) ) {
9084 sounds::sound( u.pos(), 40, sounds::sound_t::movement, _( "a rattling sound." ), true,
9085 "misc", "rattling" );
9086 }
9087 }
9088
9089 if( m.has_flag_ter_or_furn( TFLAG_HIDE_PLACE, dest_loc ) ) {
9090 add_msg( m_good, _( "You are hiding in the %s." ), m.name( dest_loc ) );
9091 }
9092
9093 if( dest_loc != u.pos() ) {
9095 }
9096
9097 tripoint oldpos = u.pos();
9098 point submap_shift = place_player( dest_loc );
9099 point ms_shift = sm_to_ms_copy( submap_shift );
9100 oldpos = oldpos - ms_shift;
9101
9102 if( pulling ) {
9103 const tripoint shifted_furn_pos = furn_pos - ms_shift;
9104 const tripoint shifted_furn_dest = furn_dest - ms_shift;
9105 const time_duration fire_age = m.get_field_age( shifted_furn_pos, fd_fire );
9106 const int fire_intensity = m.get_field_intensity( shifted_furn_pos, fd_fire );
9107 m.remove_field( shifted_furn_pos, fd_fire );
9108 m.set_field_intensity( shifted_furn_dest, fd_fire, fire_intensity );
9109 m.set_field_age( shifted_furn_dest, fd_fire, fire_age );
9110 }
9111
9112 if( u.is_hauling() ) {
9113 start_hauling( oldpos );
9114 }
9115
9117
9118 return true;
9119}
void burn_move_stamina(int moves)
Definition: character.cpp:7118
bool is_stealthy() const
Returns true if the player has stealthy movement.
virtual bool has_artifact_with(art_effect_passive effect) const
Definition: character.cpp:3213
units::mass get_weight() const override
Returns body weight plus weight of inventory and worn/wielded items.
Definition: character.cpp:3688
bool is_on_ground() const override
Returns true if the player is knocked over or has broken legs.
Definition: character.cpp:898
float mutation_value(const std::string &val) const
Goes over all mutations, gets min and max of a value with given name.
Definition: character.cpp:6644
int run_cost(int base_cost, bool diag=false) const
Returns the player's modified base movement cost.
m_size get_size() const override
Get size class of character.
Definition: character.cpp:576
bool grabbed_move(const tripoint &dp)
Check for dangerous stuff at dest_loc, return false if the player decides not to step there.
Definition: game.cpp:9732
bool is_dangerous_tile(const tripoint &dest_loc) const
Definition: game.cpp:8720
int combined_movecost(const tripoint &from, const tripoint &to, const vehicle *ignored_vehicle=nullptr, int modifier=0, bool flying=false, bool via_ramp=false) const
Cost to move out of one tile and into the next.
Definition: map.cpp:1903
m_size get_size() const override
Definition: monster.cpp:2735
std::optional< vpart_reference > part_displayed() const
Definition: vehicle.cpp:2500
std::optional< tripoint > last_target_pos
Definition: player.h:242
const std::string & str() const
Returns the identifier as plain std::string.
Definition: string_id.h:263
@ MS_TINY
Definition: creature.h:58
@ MS_LARGE
Definition: creature.h:61
@ MS_MEDIUM
Definition: creature.h:60
basic_string_view< char > string_view
Definition: fmtlib_core.h:465
static const itype_id itype_rm13_armor_on("rm13_armor_on")
static const trait_id trait_M_IMMUNE("M_IMMUNE")
@ TFLAG_SMALL_PASSAGE
Definition: mapdata.h:321
@ TFLAG_HIDE_PLACE
Definition: mapdata.h:316
@ MF_LOUDMOVES
Definition: mtype.h:175
void fungus(player &p, const tripoint &examp)
Remove furniture.
Definition: iexamine.cpp:2140
void do_obstacle(const std::string &obst="")
Definition: sounds.cpp:1634
void do_footstep()
Definition: sounds.cpp:1611

References _, action, add_msg(), AEP_MOVEMENT_NOISE, AEP_STEALTH, cata_event_dispatch::avatar_moves(), Character::burn_move_stamina(), CMM_CROUCH, CMM_RUN, CMM_WALK, map::combined_movecost(), Character::dex_cur, sfx::do_footstep(), sfx::do_obstacle(), enumerate_as_string(), fd_fire, Character::footwear_factor(), iexamine::fungus(), map::furn(), get_dangerous_tile(), map::get_field_age(), map::get_field_intensity(), avatar::get_grab_type(), Character::get_size(), monster::get_size(), Character::get_weight(), avatar::grab(), player::grab_point, grabbed_move(), Character::has_artifact_with(), Character::has_bionic(), map::has_flag(), map::has_flag_ter(), map::has_flag_ter_or_furn(), map::has_furn(), Character::has_trait(), int_id< T >::id(), map::impassable(), Character::int_cur, is_dangerous_tile(), Character::is_hauling(), Character::is_mounted(), Character::is_on_ground(), Character::is_stealthy(), Character::is_wearing(), itype_rm13_armor_on, player::last_target_pos, m, m_bad, m_good, m_warning, MAX_RECOIL, MF_LOUDMOVES, MF_RIDEABLE_MECH, Character::mod_fatigue(), Character::mounted_creature, map::move_cost(), map_data_common_t::movecost, sounds::movement, Character::movement_mode_is(), Creature::moves, MS_HUGE, MS_LARGE, MS_MEDIUM, MS_SMALL, MS_TINY, Character::mutation_value(), map::name(), int_id< T >::obj(), OBJECT_FURNITURE, OBJECT_NONE, OBJECT_VEHICLE, on_move_effects(), one_in(), optional_vpart_position::part_displayed(), place_player(), Character::pos(), Character::posx(), Character::posy(), Character::posz(), prompt_dangerous_tile(), Character::recoil, map::remove_field(), Character::run_cost(), map::set_field_age(), map::set_field_intensity(), Character::set_underwater(), sm_to_ms_copy(), sounds::sound(), start_hauling(), string_id< T >::str(), map::ter(), TFLAG_HIDE_PLACE, TFLAG_SMALL_PASSAGE, trait_M_IMMUNE, trait_PARKOUR, trigdist, tripoint_zero, u, map::veh_at(), veh_pointer_or_null(), vehicle::wheelcache, tripoint::x, tripoint::xy(), tripoint::y, and tripoint::z.

Referenced by swap_critters().

◆ win()

void game::win ( )

Marks the game as won.

Doesn't end the game.

Definition at line 2432 of file game.cpp.

2433{
2434 win_screen();
2436 memorial().add(
2437 pgettext( "memorial_male", "Closed the portal in %1$.1f days (%2$d seconds)." ),
2438 pgettext( "memorial_female", "Closed the portal in %1$.1f days (%2$d seconds)." ),
2439 to_days<float>( game_duration ), to_seconds<int>( game_duration ) );
2440 if( !u.is_dead_state() ) {
2443 }
2444}
void win_screen()
Definition: game.cpp:2446
void add(const std::string &male_msg, const std::string &female_msg)
Adds an event to the memorial log, to be written to the memorial file when the character dies.
const time_point & start_of_game
Definition: calendar.cpp:34

References achievements_tracker_ptr, memorial_logger::add(), Messages::display_messages(), get_kill_tracker(), Character::is_dead_state(), memorial(), pgettext(), show_scores_ui(), calendar::start_of_game, stats(), calendar::turn, u, and win_screen().

◆ win_screen()

void game::win_screen ( )
private

Definition at line 2446 of file game.cpp.

2447{
2448 // TODO: Move this wall somewhere
2450 std::string msg = _( "You managed to close the portal and end the invasion!" );
2451 msg += '\n';
2452 if( u.is_dead_state() ) {
2454 "Unfortunately, you had to sacrifice your life to achieve this." );
2455 msg += colorize( t, c_red ) + '\n';
2456 memorial().add(
2457 pgettext( "memorial_male", "Sacrificed his life to close the portal." ),
2458 pgettext( "memorial_female", "Sacrificed her life to close the portal." ) );
2459 } else {
2460 translation t = translation::to_translation( "win_game", "You managed to survive the ordeal." );
2461 msg += colorize( t, c_green ) + '\n';
2462 memorial().add(
2463 pgettext( "memorial_male", "Safely closed the portal." ),
2464 pgettext( "memorial_female", "Safely closed the portal." ) );
2465 }
2466 msg += string_format( _( "It took you %1$.1f days (%2$d seconds)." ),
2467 to_days<float>( game_duration ), to_seconds<int>( game_duration ) );
2468 // TODO: Print starting stats, traits, skills, all mods ever used, easiest of settings
2469 popup( msg );
2470}
Class for storing translation context and raw string for deferred translation.
Definition: translations.h:152
static translation to_translation(const std::string &raw)
Store a string, an optional plural form, and an optional context for translation.

References _, memorial_logger::add(), c_green, c_red, colorize(), Character::is_dead_state(), memorial(), pgettext(), popup(), calendar::start_of_game, string_format(), translation::to_translation(), calendar::turn, and u.

Referenced by win().

◆ write_memorial_file()

void game::write_memorial_file ( const std::string &  filename,
std::string  sLastWords 
)

Writes information about the character out to a text file timestamped with the time of the file was made.

This serves as a record of the character's state at the time the memorial was made (usually upon death) and accomplishments in a human-readable format.

Definition at line 2790 of file game.cpp.

2791{
2792 const std::string &memorial_dir = PATH_INFO::memorialdir();
2793 const std::string &memorial_active_world_dir = memorial_dir +
2794 world_generator->active_world->world_name + "/";
2795
2796 //Check if both dirs exist. Nested assure_dir_exist fails if the first dir of the nested dir does not exist.
2797 if( !assure_dir_exist( memorial_dir ) ) {
2798 debugmsg( "Could not make '%s' directory", memorial_dir );
2799 return;
2800 }
2801
2802 if( !assure_dir_exist( memorial_active_world_dir ) ) {
2803 debugmsg( "Could not make '%s' directory", memorial_active_world_dir );
2804 return;
2805 }
2806
2807 std::string path = memorial_active_world_dir + filename + ".txt";
2808
2809 write_to_file( path, [&]( std::ostream & fout ) {
2810 memorial().write( fout, sLastWords );
2811 }, _( "player memorial" ) );
2812}
void write(std::ostream &memorial_file, const std::string &epitaph) const
std::string memorialdir()
Definition: path_info.cpp:222

References _, assure_dir_exist(), debugmsg, memorial(), PATH_INFO::memorialdir(), world_generator, memorial_logger::write(), and write_to_file().

Referenced by cleanup_at_end().

◆ zones_manager()

void game::zones_manager ( )

Definition at line 6125 of file game.cpp.

6126{
6127 const tripoint stored_view_offset = u.view_offset;
6128
6130
6131 const int zone_ui_height = 12;
6132 const int zone_options_height = 7;
6133
6134 const int width = 45;
6135
6136 int offsetX = 0;
6137 int max_rows = 0;
6138
6139 catacurses::window w_zones;
6140 catacurses::window w_zones_border;
6141 catacurses::window w_zones_info;
6142 catacurses::window w_zones_info_border;
6143 catacurses::window w_zones_options;
6144
6145 bool show = true;
6146
6147 ui_adaptor ui;
6148 ui.on_screen_resize( [&]( ui_adaptor & ui ) {
6149 if( !show ) {
6150 ui.position( point_zero, point_zero );
6151 return;
6152 }
6153 offsetX = get_option<std::string>( "SIDEBAR_POSITION" ) != "left" ?
6154 TERMX - width : 0;
6155 const int w_zone_height = TERMY - zone_ui_height;
6156 max_rows = w_zone_height - 2;
6157 w_zones = catacurses::newwin( w_zone_height - 2, width - 2,
6158 point( offsetX + 1, 1 ) );
6159 w_zones_border = catacurses::newwin( w_zone_height, width,
6160 point( offsetX, 0 ) );
6161 w_zones_info = catacurses::newwin( zone_ui_height - zone_options_height - 1,
6162 width - 2, point( offsetX + 1, w_zone_height ) );
6163 w_zones_info_border = catacurses::newwin( zone_ui_height, width,
6164 point( offsetX, w_zone_height ) );
6165 w_zones_options = catacurses::newwin( zone_options_height - 1, width - 2,
6166 point( offsetX + 1, TERMY - zone_options_height ) );
6167
6168 ui.position( point( offsetX, 0 ), point( width, TERMY ) );
6169 } );
6170 ui.mark_resize();
6171
6172 std::string action;
6173 input_context ctxt( "ZONES_MANAGER" );
6174 ctxt.register_cardinal();
6175 ctxt.register_action( "CONFIRM" );
6176 ctxt.register_action( "QUIT" );
6177 ctxt.register_action( "ADD_ZONE" );
6178 ctxt.register_action( "REMOVE_ZONE" );
6179 ctxt.register_action( "MOVE_ZONE_UP" );
6180 ctxt.register_action( "MOVE_ZONE_DOWN" );
6181 ctxt.register_action( "SHOW_ZONE_ON_MAP" );
6182 ctxt.register_action( "ENABLE_ZONE" );
6183 ctxt.register_action( "DISABLE_ZONE" );
6184 ctxt.register_action( "SHOW_ALL_ZONES" );
6185 ctxt.register_action( "HELP_KEYBINDINGS" );
6186
6187 auto &mgr = zone_manager::get_manager();
6188 int start_index = 0;
6189 int active_index = 0;
6190 bool blink = false;
6191 bool stuff_changed = false;
6192 bool show_all_zones = false;
6193 int zone_cnt = 0;
6194
6195 // get zones on the same z-level, with distance between player and
6196 // zone center point <= 50 or all zones, if show_all_zones is true
6197 auto get_zones = [&]() {
6198 std::vector<zone_manager::ref_zone_data> zones;
6199 if( show_all_zones ) {
6200 zones = mgr.get_zones();
6201 } else {
6202 const tripoint &u_abs_pos = m.getabs( u.pos() );
6203 for( zone_manager::ref_zone_data &ref : mgr.get_zones() ) {
6204 const tripoint &zone_abs_pos = ref.get().get_center_point();
6205 if( u_abs_pos.z == zone_abs_pos.z && rl_dist( u_abs_pos, zone_abs_pos ) <= 50 ) {
6206 zones.emplace_back( ref );
6207 }
6208 }
6209 }
6210 zone_cnt = static_cast<int>( zones.size() );
6211 return zones;
6212 };
6213
6214 auto zones = get_zones();
6215
6216 auto zones_manager_options = [&]() {
6217 werase( w_zones_options );
6218
6219 if( zone_cnt > 0 ) {
6220 const auto &zone = zones[active_index].get();
6221
6222 if( zone.has_options() ) {
6223 const auto &descriptions = zone.get_options().get_descriptions();
6224
6225 // NOLINTNEXTLINE(cata-use-named-point-constants)
6226 mvwprintz( w_zones_options, point( 1, 0 ), c_white, _( "Options" ) );
6227
6228 int y = 1;
6229 for( const auto &desc : descriptions ) {
6230 mvwprintz( w_zones_options, point( 3, y ), c_white, desc.first );
6231 mvwprintz( w_zones_options, point( 20, y ), c_white, desc.second );
6232 y++;
6233 }
6234 }
6235 }
6236
6237 wnoutrefresh( w_zones_options );
6238 };
6239
6240 std::optional<tripoint> zone_start;
6241 std::optional<tripoint> zone_end;
6242 bool zone_blink = false;
6243 bool zone_cursor = false;
6245 zone_start, zone_end, zone_blink, zone_cursor );
6246 add_draw_callback( zone_cb );
6247
6248 auto query_position =
6249 [&]() -> std::optional<std::pair<tripoint, tripoint>> {
6250 on_out_of_scope invalidate_current_ui( [&]()
6251 {
6252 ui.mark_resize();
6253 } );
6254 restore_on_out_of_scope<bool> show_prev( show );
6255 restore_on_out_of_scope<std::optional<tripoint>> zone_start_prev( zone_start );
6256 restore_on_out_of_scope<std::optional<tripoint>> zone_end_prev( zone_end );
6257 show = false;
6258 zone_start = std::nullopt;
6259 zone_end = std::nullopt;
6260 ui.mark_resize();
6261
6263 popup.on_top( true );
6264 popup.message( "%s", _( "Select first point." ) );
6265
6267
6268 const look_around_result first = look_around( /*show_window=*/false, center, center, false, true,
6269 false );
6270 if( first.position )
6271 {
6272 popup.message( "%s", _( "Select second point." ) );
6273
6274 const look_around_result second = look_around( /*show_window=*/false, center, *first.position,
6275 true, true, false );
6276 if( second.position ) {
6277 tripoint first_abs = m.getabs( tripoint( std::min( first.position->x,
6278 second.position->x ),
6279 std::min( first.position->y, second.position->y ),
6280 std::min( first.position->z,
6281 second.position->z ) ) );
6282 tripoint second_abs = m.getabs( tripoint( std::max( first.position->x,
6283 second.position->x ),
6284 std::max( first.position->y, second.position->y ),
6285 std::max( first.position->z,
6286 second.position->z ) ) );
6287 return std::pair<tripoint, tripoint>( first_abs, second_abs );
6288 }
6289 }
6290
6291 return std::nullopt;
6292 };
6293
6294 ui.on_redraw( [&]( const ui_adaptor & ) {
6295 if( !show ) {
6296 return;
6297 }
6298 zones_manager_draw_borders( w_zones_border, w_zones_info_border, zone_ui_height, width );
6299 zones_manager_shortcuts( w_zones_info );
6300
6301 if( zone_cnt == 0 ) {
6302 werase( w_zones );
6303 mvwprintz( w_zones, point( 2, 5 ), c_white, _( "No Zones defined." ) );
6304
6305 } else {
6306 werase( w_zones );
6307
6308 calcStartPos( start_index, active_index, max_rows, zone_cnt );
6309
6310 draw_scrollbar( w_zones_border, active_index, max_rows, zone_cnt, point_south );
6311 wnoutrefresh( w_zones_border );
6312
6313 int iNum = 0;
6314
6315 tripoint player_absolute_pos = m.getabs( u.pos() );
6316
6317 //Display saved zones
6318 for( auto &i : zones ) {
6319 if( iNum >= start_index &&
6320 iNum < start_index + ( ( max_rows > zone_cnt ) ? zone_cnt : max_rows ) ) {
6321 const auto &zone = i.get();
6322
6323 nc_color colorLine = ( zone.get_enabled() ) ? c_white : c_light_gray;
6324
6325 if( iNum == active_index ) {
6326 mvwprintz( w_zones, point( 0, iNum - start_index ), c_yellow, "%s", ">>" );
6327 colorLine = ( zone.get_enabled() ) ? c_light_green : c_green;
6328 }
6329
6330 //Draw Zone name
6331 mvwprintz( w_zones, point( 3, iNum - start_index ), colorLine,
6332 trim_by_length( zone.get_name(), 15 ) );
6333
6334 //Draw Type name
6335 mvwprintz( w_zones, point( 20, iNum - start_index ), colorLine,
6336 mgr.get_name_from_type( zone.get_type() ) );
6337
6338 tripoint center = zone.get_center_point();
6339
6340 //Draw direction + distance
6341 mvwprintz( w_zones, point( 32, iNum - start_index ), colorLine, "%*d %s",
6342 5, static_cast<int>( trig_dist( player_absolute_pos, center ) ),
6343 direction_name_short( direction_from( player_absolute_pos,
6344 center ) ) );
6345
6346 //Draw Vehicle Indicator
6347 mvwprintz( w_zones, point( 41, iNum - start_index ), colorLine,
6348 zone.get_is_vehicle() ? "*" : "" );
6349 }
6350 iNum++;
6351 }
6352
6353 // Display zone options
6354 zones_manager_options();
6355 }
6356
6357 wnoutrefresh( w_zones );
6358 } );
6359
6360 zones_manager_open = true;
6361 do {
6362 if( action == "ADD_ZONE" ) {
6363 do { // not a loop, just for quick bailing out if canceled
6364 const auto maybe_id = mgr.query_type();
6365 if( !maybe_id.has_value() ) {
6366 break;
6367 }
6368
6369 const zone_type_id &id = maybe_id.value();
6370 auto options = zone_options::create( id );
6371
6372 if( !options->query_at_creation() ) {
6373 break;
6374 }
6375
6376 auto default_name = options->get_zone_name_suggestion();
6377 if( default_name.empty() ) {
6378 default_name = mgr.get_name_from_type( id );
6379 }
6380 const auto maybe_name = mgr.query_name( default_name );
6381 if( !maybe_name.has_value() ) {
6382 break;
6383 }
6384 const std::string &name = maybe_name.value();
6385
6386 const auto position = query_position();
6387 if( !position ) {
6388 break;
6389 }
6390
6391 mgr.add( name, id, g->u.get_faction()->id, false, true, position->first,
6392 position->second, options );
6393
6394 zones = get_zones();
6395 active_index = zone_cnt - 1;
6396
6397 stuff_changed = true;
6398 } while( false );
6399
6400 blink = false;
6401 } else if( action == "SHOW_ALL_ZONES" ) {
6402 show_all_zones = !show_all_zones;
6403 zones = get_zones();
6404 active_index = 0;
6405 } else if( zone_cnt > 0 ) {
6406 if( action == "UP" ) {
6407 active_index--;
6408 if( active_index < 0 ) {
6409 active_index = zone_cnt - 1;
6410 }
6411 blink = false;
6412 } else if( action == "DOWN" ) {
6413 active_index++;
6414 if( active_index >= zone_cnt ) {
6415 active_index = 0;
6416 }
6417 blink = false;
6418 } else if( action == "REMOVE_ZONE" ) {
6419 if( active_index < zone_cnt ) {
6420 mgr.remove( zones[active_index] );
6421 zones = get_zones();
6422 active_index--;
6423
6424 if( active_index < 0 ) {
6425 active_index = 0;
6426 }
6427 }
6428 blink = false;
6429 stuff_changed = true;
6430
6431 } else if( action == "CONFIRM" ) {
6432 auto &zone = zones[active_index].get();
6433
6434 uilist as_m;
6435 as_m.text = _( "What do you want to change:" );
6436 as_m.entries.emplace_back( 1, true, '1', _( "Edit name" ) );
6437 as_m.entries.emplace_back( 2, true, '2', _( "Edit type" ) );
6438 as_m.entries.emplace_back( 3, zone.get_options().has_options(), '3',
6439 zone.get_type() == zone_type_id( "LOOT_CUSTOM" ) ? _( "Edit filter" ) : _( "Edit options" ) );
6440 as_m.entries.emplace_back( 4, !zone.get_is_vehicle(), '4', _( "Edit position" ) );
6441 // TODO: Enable moving vzone after vehicle zone can be bigger than 1*1
6442 as_m.entries.emplace_back( 5, !zone.get_is_vehicle(), '5', _( "Move position" ) );
6443 as_m.query();
6444
6445 switch( as_m.ret ) {
6446 case 1:
6447 if( zone.set_name() ) {
6448 stuff_changed = true;
6449 }
6450 break;
6451 case 2:
6452 if( zone.set_type() ) {
6453 stuff_changed = true;
6454 }
6455 break;
6456 case 3:
6457 if( zone.get_options().query() ) {
6458 stuff_changed = true;
6459 }
6460 break;
6461 case 4: {
6462 const auto pos = query_position();
6463 if( pos && ( pos->first != zone.get_start_point() ||
6464 pos->second != zone.get_end_point() ) ) {
6465 zone.set_position( *pos );
6466 stuff_changed = true;
6467 }
6468 break;
6469 }
6470 case 5: {
6471 on_out_of_scope invalidate_current_ui( [&]() {
6472 ui.mark_resize();
6473 } );
6474 restore_on_out_of_scope<bool> show_prev( show );
6475 restore_on_out_of_scope<std::optional<tripoint>> zone_start_prev( zone_start );
6476 restore_on_out_of_scope<std::optional<tripoint>> zone_end_prev( zone_end );
6477 show = false;
6478 zone_start = std::nullopt;
6479 zone_end = std::nullopt;
6480 ui.mark_resize();
6481 static_popup message_pop;
6482 message_pop.on_top( true );
6483 message_pop.message( "%s", _( "Moving zone." ) );
6484 const auto zone_local_start_point = m.getlocal( zone.get_start_point() );
6485 const auto zone_local_end_point = m.getlocal( zone.get_end_point() );
6486 // local position of the zone center, used to calculate the u.view_offset,
6487 // could center the screen to the position it represents
6488 auto view_center = m.getlocal( zone.get_center_point() );
6489 const look_around_result result_local = look_around( false, view_center,
6490 zone_local_start_point, false, false,
6491 false, true, zone_local_end_point );
6492 if( result_local.position ) {
6493 const auto new_start_point = m.getabs( *result_local.position );
6494 if( new_start_point == zone.get_start_point() ) {
6495 break; // Nothing changed, don't save
6496 }
6497
6498 const auto new_end_point = zone.get_end_point() - zone.get_start_point() + new_start_point;
6499 zone.set_position( std::pair<tripoint, tripoint>( new_start_point, new_end_point ) );
6500 stuff_changed = true;
6501 }
6502 }
6503 break;
6504 default:
6505 break;
6506 }
6507
6508 blink = false;
6509 } else if( action == "MOVE_ZONE_UP" && zone_cnt > 1 ) {
6510 if( active_index < zone_cnt - 1 ) {
6511 mgr.swap( zones[active_index], zones[active_index + 1] );
6512 zones = get_zones();
6513 active_index++;
6514 }
6515 blink = false;
6516 stuff_changed = true;
6517
6518 } else if( action == "MOVE_ZONE_DOWN" && zone_cnt > 1 ) {
6519 if( active_index > 0 ) {
6520 mgr.swap( zones[active_index], zones[active_index - 1] );
6521 zones = get_zones();
6522 active_index--;
6523 }
6524 blink = false;
6525 stuff_changed = true;
6526
6527 } else if( action == "SHOW_ZONE_ON_MAP" ) {
6528 //show zone position on overmap;
6529 tripoint_abs_omt player_overmap_position = u.global_omt_location();
6530 // TODO: fix point types
6531 tripoint_abs_omt zone_overmap( ms_to_omt_copy( zones[active_index].get().get_center_point() ) );
6532
6533 ui::omap::display_zones( player_overmap_position, zone_overmap, active_index );
6534 } else if( action == "ENABLE_ZONE" ) {
6535 zones[active_index].get().set_enabled( true );
6536
6537 stuff_changed = true;
6538
6539 } else if( action == "DISABLE_ZONE" ) {
6540 zones[active_index].get().set_enabled( false );
6541
6542 stuff_changed = true;
6543 }
6544 }
6545
6546 if( zone_cnt > 0 ) {
6547 blink = !blink;
6548 const auto &zone = zones[active_index].get();
6549 zone_start = m.getlocal( zone.get_start_point() );
6550 zone_end = m.getlocal( zone.get_end_point() );
6551 ctxt.set_timeout( get_option<int>( "BLINK_SPEED" ) );
6552 } else {
6553 blink = false;
6554 zone_start = zone_end = std::nullopt;
6555 ctxt.reset_timeout();
6556 }
6557
6558 // Actually accessed from the terrain overlay callback `zone_cb` in the
6559 // call to `ui_manager::redraw`.
6560 //NOLINTNEXTLINE(clang-analyzer-deadcode.DeadStores)
6561 zone_blink = blink;
6563
6565
6566 //Wait for input
6567 action = ctxt.handle_input();
6568 } while( action != "QUIT" );
6569 zones_manager_open = false;
6570 ctxt.reset_timeout();
6571 zone_cb = nullptr;
6572
6573 if( stuff_changed ) {
6574 auto &zones = zone_manager::get_manager();
6575 if( query_yn( _( "Save changes?" ) ) ) {
6576 zones.save_zones();
6577 } else {
6578 zones.load_zones();
6579 }
6580
6581 zones.cache_data();
6582 }
6583
6584 u.view_offset = stored_view_offset;
6585}
query_popup & on_top(bool top)
Whether to show the popup on the top of the screen.
Definition: popup.cpp:59
std::reference_wrapper< zone_data > ref_zone_data
Definition: clzones.h:342
static shared_ptr_fast< zone_options > create(const zone_type_id &type)
Definition: clzones.cpp:187
int trig_dist(const coords::coord_point< Point, Origin, Scale > &loc1, const coords::coord_point< Point, Origin, Scale > &loc2)
Definition: coordinates.h:512
static void zones_manager_shortcuts(const catacurses::window &w_info)
Definition: game.cpp:6060
static void zones_manager_draw_borders(const catacurses::window &w_border, const catacurses::window &w_info_border, const int iInfoHeight, const int width)
Definition: game.cpp:6083
void optional(const JsonObject &jo, const bool was_loaded, const std::string &name, MemberType &member)
std::string options()
Definition: path_info.cpp:230
const std::set< itype_id > & get()
void display_zones(const tripoint_abs_omt &center, const tripoint_abs_omt &select, int iZoneIndex)
Display overmap like with display() and display the given zone.
std::string trim_by_length(const std::string &text, int width)
Definition: output.cpp:224
std::optional< tripoint > position
Definition: game.h:127

References _, action, add_draw_callback(), c_green, c_light_gray, c_light_green, c_white, c_yellow, calcStartPos(), center, zone_options::create(), create_zone_callback(), direction_from(), direction_name_short(), ui::omap::display_zones(), draw_scrollbar(), uilist::entries, g, charge_removal_blacklist::get(), zone_manager::get_manager(), map::getabs(), map::getlocal(), Character::global_omt_location(), input_context::handle_input(), invalidate_main_ui_adaptor(), look_around(), m, query_popup::message(), ms_to_omt_copy(), mvwprintz(), om_direction::name(), catacurses::newwin(), query_popup::on_top(), optional(), PATH_INFO::options(), point_south, point_zero, popup(), Character::pos(), look_around_result::position, uilist::query(), query_yn(), ui_manager::redraw(), input_context::register_action(), input_context::register_cardinal(), input_context::reset_timeout(), uilist::ret, rl_dist(), second, input_context::set_timeout(), TERMX, TERMY, uilist::text, trig_dist(), trim_by_length(), tripoint_zero, u, player::view_offset, catacurses::werase(), catacurses::wnoutrefresh(), tripoint::z, zones_manager_draw_borders(), zones_manager_open, and zones_manager_shortcuts().

Referenced by handle_action().

◆ zoom_in()

void game::zoom_in ( )

Definition at line 7087 of file game.cpp.

7088{
7089#if defined(TILES)
7090 if( tileset_zoom == 64 ) {
7091 tileset_zoom = MAXIMUM_ZOOM_LEVEL;
7092 } else {
7094 }
7095 rescale_tileset( tileset_zoom );
7096#endif
7097}

References tileset_zoom.

Referenced by handle_action(), and look_around().

◆ zoom_out()

void game::zoom_out ( )

Definition at line 7075 of file game.cpp.

7076{
7077#if defined(TILES)
7078 if( tileset_zoom > MAXIMUM_ZOOM_LEVEL ) {
7080 } else {
7081 tileset_zoom = 64;
7082 }
7083 rescale_tileset( tileset_zoom );
7084#endif
7085}

References tileset_zoom.

Referenced by handle_action(), and look_around().

Friends And Related Function Documentation

◆ advanced_inventory

friend class advanced_inventory
friend

Definition at line 146 of file game.h.

◆ Creature_range

friend class Creature_range
friend

Definition at line 334 of file game.h.

Referenced by all_creatures().

◆ editmap

friend class editmap
friend

Definition at line 145 of file game.h.

◆ get_avatar

avatar & get_avatar ( )
friend

Definition at line 105 of file avatar.cpp.

106{
107 return g->u;
108}

Referenced by butcher_submenu(), and get_player_base_save_path().

◆ get_distribution_grid_tracker

distribution_grid_tracker & get_distribution_grid_tracker ( )
friend

Returns distribution grid tracker that is a part of the global game *g.

game TODO: This wouldn't be required in an ideal world

Definition at line 12117 of file game.cpp.

12118{
12119 return *g->grid_tracker_ptr;
12120}

◆ get_map

map & get_map ( )
friend

◆ get_player_character

Character & get_player_character ( )
friend

Definition at line 403 of file character.cpp.

404{
405 return g->u;
406}

◆ get_weather

weather_manager & get_weather ( )
friend

Definition at line 64 of file weather.cpp.

65{
66 return *g->weather_manager_ptr;
67}

Referenced by do_turn(), get_player_input(), is_in_sunlight(), load(), natural_light_level(), place_player_overmap(), serialize_master(), setup(), start_game(), and unserialize_master().

◆ main_menu

friend class main_menu
friend

Definition at line 147 of file game.h.

◆ monster_range

friend class monster_range
friend

Definition at line 333 of file game.h.

Referenced by all_monsters().

Member Data Documentation

◆ achievements_tracker_ptr

pimpl<achievements_tracker> game::achievements_tracker_ptr
private

Definition at line 954 of file game.h.

Referenced by death_screen(), game(), handle_action(), serialize(), setup(), unserialize(), and win().

◆ active_npc

◆ auto_travel_mode

bool game::auto_travel_mode = false

Definition at line 1017 of file game.h.

Referenced by handle_action(), serialize(), and unserialize().

◆ bVMonsterLookFire

bool game::bVMonsterLookFire = false
private

Definition at line 1034 of file game.h.

Referenced by list_monsters(), look_around(), and setup().

◆ coming_to_stairs

std::vector<monster> game::coming_to_stairs

◆ critter_died

bool game::critter_died = false
private

Has anything died in this turn and needs to be cleaned up?

Definition at line 1048 of file game.h.

Referenced by cleanup_dead(), and set_critter_died().

◆ critter_tracker

◆ debug_hour_timer

◆ debug_pathfinding

bool game::debug_pathfinding = false

Definition at line 998 of file game.h.

◆ debug_submap_grid_overlay

bool game::debug_submap_grid_overlay = false

Definition at line 999 of file game.h.

◆ destination_preview

std::vector<tripoint> game::destination_preview
private

◆ displaying_lighting_condition

int game::displaying_lighting_condition = 0

Type of lighting condition overlay to display.

Definition at line 1011 of file game.h.

◆ displaying_overlays

std::optional<action_id> game::displaying_overlays
private

Definition at line 917 of file game.h.

Referenced by display_overlay_state(), and display_toggle_overlay().

◆ displaying_visibility_creature

Creature* game::displaying_visibility_creature

Creature for which to display the visibility map.

Definition at line 1009 of file game.h.

Referenced by display_visibility().

◆ draw_callbacks

std::vector<weak_ptr_fast<draw_callback_t> > game::draw_callbacks
private

Definition at line 225 of file game.h.

Referenced by add_draw_callback(), and draw().

◆ driving_view_offset

point game::driving_view_offset

Definition at line 996 of file game.h.

Referenced by calc_driving_offset(), do_turn(), handle_action(), and set_driving_view_offset().

◆ event_bus_ptr

pimpl<event_bus> game::event_bus_ptr
private

Definition at line 951 of file game.h.

Referenced by events().

◆ faction_manager_ptr

◆ first_redraw_since_waiting_started

bool game::first_redraw_since_waiting_started = true
private

Is this the first redraw since waiting (sleeping or activity) started.

Definition at line 1050 of file game.h.

Referenced by do_turn(), and game().

◆ follower_ids

std::set<character_id> game::follower_ids
private

◆ fullscreen

bool game::fullscreen = false

◆ gamemode

std::unique_ptr<special_game> game::gamemode
private

◆ grid_tracker_ptr

pimpl<distribution_grid_tracker> game::grid_tracker_ptr
private

Definition at line 957 of file game.h.

Referenced by do_turn(), load_map(), on_options_changed(), and update_map().

◆ is_looking

bool game::is_looking = false
private

Definition at line 224 of file game.h.

Referenced by draw_ter(), and look_around().

◆ kill_tracker_ptr

pimpl<kill_tracker> game::kill_tracker_ptr
private

Definition at line 953 of file game.h.

Referenced by game(), get_kill_tracker(), serialize(), and unserialize().

◆ last_mouse_edge_scroll

std::chrono::time_point<std::chrono::steady_clock> game::last_mouse_edge_scroll
private

Definition at line 1067 of file game.h.

Referenced by mouse_edge_scrolling().

◆ last_mouse_edge_scroll_vector_overmap

tripoint game::last_mouse_edge_scroll_vector_overmap
private

Definition at line 1069 of file game.h.

Referenced by mouse_edge_scrolling_overmap(), and mouse_edge_scrolling_terrain().

◆ last_mouse_edge_scroll_vector_terrain

tripoint game::last_mouse_edge_scroll_vector_terrain
private

Definition at line 1068 of file game.h.

Referenced by mouse_edge_scrolling_overmap(), and mouse_edge_scrolling_terrain().

◆ last_save_timestamp

time_t game::last_save_timestamp
private

Definition at line 1040 of file game.h.

Referenced by autosave(), init_autosave(), and quicksave().

◆ latest_lightlevels

std::array<float, OVERMAP_LAYERS> game::latest_lightlevels
mutableprivate

Definition at line 1041 of file game.h.

Referenced by natural_light_level(), and reset_light_level().

◆ list_item_downvote

std::string game::list_item_downvote
private

Definition at line 1031 of file game.h.

Referenced by list_items().

◆ list_item_upvote

std::string game::list_item_upvote
private

Definition at line 1030 of file game.h.

Referenced by list_items().

◆ liveview

live_view& game::liveview
private

Definition at line 948 of file game.h.

Referenced by draw_look_around_cursor(), and handle_mouseview().

◆ liveview_ptr

pimpl<live_view> game::liveview_ptr
private

Definition at line 947 of file game.h.

◆ m

map& game::m

Definition at line 961 of file game.h.

Referenced by autopilot_vehicles(), cata_event_dispatch::avatar_moves(), butcher(), catch_a_monster(), chat(), check_near_zone(), check_zone(), control_vehicle(), delete_cyborg_item(), disable_robot(), disp_NPCs(), do_turn(), draw(), draw_bullet(), draw_critter(), draw_critter_highlighted(), draw_critter_internal(), draw_hit_mon(), draw_look_around_cursor(), draw_ter(), examine(), extended_description(), find_nearby_items(), find_or_make_stairs(), fling_creature(), forced_door_closing(), get_cur_om(), get_dangerous_tile(), get_fishable_locations(), get_levx(), get_levy(), get_levz(), get_player_input(), get_veh_dir_indicator_location(), grabbed_furn_move(), grabbed_veh_move(), handle_action(), is_empty(), is_game_over(), is_in_sunlight(), is_sheltered(), knockback(), list_items(), list_monsters(), load(), load_map(), load_npcs(), look_around(), mon_info_update(), monmove(), moving_vehicle_dismount(), peek(), perhaps_add_random_npc(), phasing_move(), pickup(), place_critter_around(), place_player(), place_player_overmap(), place_vehicle_nearby(), pre_print_all_tile_info(), print_all_tile_info(), print_fields_info(), print_graffiti_info(), print_items_info(), print_terrain_info(), print_trap_info(), process_artifact(), prompt_dangerous_tile(), remoteveh(), save_maps(), serialize(), setup(), shift_monsters(), start_game(), start_hauling(), swap_critters(), try_get_left_click_action(), try_get_right_click_action(), update_map(), update_stair_monsters(), use_computer(), validate_camps(), validate_linked_vehicles(), validate_mounted_npcs(), vertical_move(), vertical_notes(), vertical_shift(), walk_move(), and zones_manager().

◆ main_ui_adaptor

weak_ptr_fast<ui_adaptor> game::main_ui_adaptor
private

◆ map_ptr

pimpl<map> game::map_ptr
private

Definition at line 945 of file game.h.

◆ memorial_logger_ptr

pimpl<memorial_logger> game::memorial_logger_ptr
private

Definition at line 955 of file game.h.

Referenced by game(), and memorial().

◆ monstairz

int game::monstairz = 0

Definition at line 983 of file game.h.

Referenced by update_stair_monsters(), and vertical_move().

◆ mostseen

int game::mostseen = 0

◆ moves_since_last_save

int game::moves_since_last_save = 0
private

Definition at line 1039 of file game.h.

Referenced by do_turn(), get_moves_since_last_save(), init_autosave(), quickload(), and quicksave().

◆ new_game

bool game::new_game = false

True if the game has just started or loaded, else false.

Definition at line 979 of file game.h.

Referenced by do_turn(), setup(), and start_game().

◆ next_mission_id

int game::next_mission_id = 0
private

Definition at line 1037 of file game.h.

Referenced by assign_mission_id(), serialize_master(), setup(), and unserialize_master().

◆ next_npc_id

character_id game::next_npc_id
private

Definition at line 1035 of file game.h.

Referenced by assign_npc_id(), serialize_master(), setup(), and unserialize_master().

◆ npcs_dirty

bool game::npcs_dirty = false
private

Has a NPC been spawned since last load?

Definition at line 1046 of file game.h.

Referenced by do_turn(), load_npcs(), and set_npcs_dirty().

◆ queue_screenshot

bool game::queue_screenshot = false

Definition at line 1018 of file game.h.

Referenced by do_turn().

◆ remoteveh_cache

vehicle* game::remoteveh_cache
private

Definition at line 1044 of file game.h.

Referenced by remoteveh(), setremoteveh(), and setup().

◆ remoteveh_cache_time

time_point game::remoteveh_cache_time
private

Definition at line 1043 of file game.h.

Referenced by remoteveh(), setremoteveh(), and setup().

◆ right_sidebar

bool game::right_sidebar = false

Definition at line 1014 of file game.h.

◆ safe_mode

◆ safe_mode_warning_logged

bool game::safe_mode_warning_logged = false
private

Definition at line 1033 of file game.h.

Referenced by check_safe_mode_allowed(), handle_action(), and set_safe_mode().

◆ scen

const scenario* game::scen = nullptr

Definition at line 981 of file game.h.

Referenced by start_calendar(), and start_game().

◆ scent

scent_map& game::scent

Definition at line 963 of file game.h.

Referenced by display_scent(), do_turn(), serialize(), setup(), unserialize(), update_map(), and vertical_shift().

◆ scent_ptr

pimpl<scent_map> game::scent_ptr
private

Definition at line 949 of file game.h.

◆ seed

unsigned int game::seed = 0
private

Seed for all the random numbers that should have consistent randomness (weather).

Definition at line 1062 of file game.h.

Referenced by get_seed(), serialize_master(), start_game(), and unserialize_master().

◆ sFilter

std::string game::sFilter
private

Definition at line 1029 of file game.h.

Referenced by list_items(), and reset_item_list_state().

◆ show_panel_adm

bool game::show_panel_adm = false

Definition at line 1013 of file game.h.

Referenced by draw_panels(), and load_static_data().

◆ spell_events_ptr

pimpl<spell_events> game::spell_events_ptr
private

Definition at line 956 of file game.h.

Referenced by game(), and spell_events_subscriber().

◆ stats_tracker_ptr

pimpl<stats_tracker> game::stats_tracker_ptr
private

Definition at line 952 of file game.h.

Referenced by game(), serialize(), stats(), and unserialize().

◆ ter_view_p

tripoint game::ter_view_p

Definition at line 985 of file game.h.

Referenced by draw(), and draw_ter().

◆ tileset_zoom

int game::tileset_zoom = 0
private

How far the tileset should be zoomed out, 16 is default.

32 is zoomed in by x2, 8 is zoomed out by x0.5

Definition at line 1059 of file game.h.

Referenced by get_zoom(), look_around(), mouse_edge_scrolling_terrain(), reset_zoom(), set_zoom(), zoom_in(), and zoom_out().

◆ timed_event_manager_ptr

pimpl<timed_event_manager> game::timed_event_manager_ptr
private

Definition at line 950 of file game.h.

◆ timed_events

timed_event_manager& game::timed_events

Definition at line 964 of file game.h.

Referenced by do_turn(), natural_light_level(), and setup().

◆ token_provider_ptr

pimpl<drop_token_provider> game::token_provider_ptr

Definition at line 974 of file game.h.

Referenced by serialize(), setup(), and unserialize().

◆ turnssincelastmon

int game::turnssincelastmon = 0

Definition at line 1020 of file game.h.

Referenced by handle_action(), mon_info_update(), and setup().

◆ u

avatar& game::u

Definition at line 962 of file game.h.

Referenced by add_artifact_dreams(), add_npc_follower(), autopilot_vehicles(), cata_event_dispatch::avatar_moves(), butcher(), calc_driving_offset(), cancel_activity_or_ignore_query(), cancel_activity_query(), catch_a_monster(), centerlistview(), chat(), check_safe_mode_allowed(), cleanup_at_end(), control_vehicle(), create_starting_npcs(), critter_at(), critter_by_id(), death_screen(), disable_robot(), disp_NPCs(), display_scent(), do_turn(), draw(), draw_critter(), draw_critter_highlighted(), draw_critter_internal(), draw_hit_mon(), draw_line(), draw_look_around_cursor(), draw_minimap(), draw_panels(), draw_ter(), draw_trail_to_square(), draw_veh_dir_indicator(), drop(), drop_in_direction(), exam_vehicle(), examine(), extended_description(), find_nearby_items(), find_or_make_stairs(), fling_creature(), forced_door_closing(), fungal_effects::fungalize(), get_dangerous_tile(), get_player_input(), get_veh_dir_indicator_location(), grabbed_furn_move(), grabbed_move(), grabbed_veh_move(), handle_action(), handle_key_blocking_activity(), inv_map_splice(), is_game_over(), is_hostile_within(), is_in_viewport(), item_action_menu(), knockback(), list_items(), list_items_monsters(), list_missions(), list_monsters(), load(), look_around(), mon_info(), mon_info_update(), monmove(), move_save_to_graveyard(), moving_vehicle_dismount(), npc_menu(), on_move_effects(), open_consume_item_menu(), overmap_npc_move(), peek(), perhaps_add_random_npc(), phasing_move(), pickup_feet(), place_player(), place_player_overmap(), print_all_tile_info(), print_creature_info(), print_items_info(), print_terrain_info(), print_trap_info(), process_activity(), process_artifact(), process_voluntary_act_interrupt(), prompt_dangerous_tile(), quickload(), remoteveh(), remove_npc_follower(), save(), save_player_data(), serialize(), set_driving_view_offset(), setremoteveh(), shared_from(), slip_down(), fungal_effects::spread_fungus_one_tile(), start_game(), start_hauling(), toggle_gate(), try_get_left_click_action(), try_get_right_click_action(), unserialize(), update_map(), update_overmap_seen(), update_stair_monsters(), use_computer(), validate_camps(), validate_npc_followers(), vertical_move(), vertical_notes(), vertical_shift(), walk_move(), win(), win_screen(), and zones_manager().

◆ u_ptr

pimpl<avatar> game::u_ptr
private

Definition at line 946 of file game.h.

◆ u_shared_ptr

shared_ptr_fast<player> game::u_shared_ptr
private

Definition at line 1024 of file game.h.

Referenced by shared_from().

◆ uquit

quit_status game::uquit

Used in main.cpp to determine what type of quit is being performed.

Definition at line 977 of file game.h.

Referenced by cleanup_at_end(), do_turn(), get_player_input(), handle_action(), is_game_over(), and setup().

◆ user_action_counter

int game::user_action_counter = 0
private

Definition at line 1056 of file game.h.

Referenced by get_user_action_counter(), and handle_action().

◆ w_minimap

catacurses::window game::w_minimap

Definition at line 989 of file game.h.

Referenced by create_or_get_main_ui_adaptor(), and draw_minimap().

◆ w_minimap_ptr

catacurses::window game::w_minimap_ptr
private

Definition at line 1027 of file game.h.

Referenced by create_or_get_main_ui_adaptor().

◆ w_omlegend

catacurses::window game::w_omlegend

Definition at line 988 of file game.h.

◆ w_overmap

catacurses::window game::w_overmap

Definition at line 987 of file game.h.

◆ w_pixel_minimap

catacurses::window game::w_pixel_minimap

◆ w_terrain

◆ w_terrain_ptr

catacurses::window game::w_terrain_ptr
private

Definition at line 1026 of file game.h.

Referenced by create_or_get_main_ui_adaptor().

◆ wait_popup

std::unique_ptr<static_popup> game::wait_popup
private

Definition at line 1075 of file game.h.

Referenced by do_turn().

◆ was_fullscreen

bool game::was_fullscreen = false

Definition at line 1016 of file game.h.

Referenced by load_static_data(), reenter_fullscreen(), and temp_exit_fullscreen().

◆ weather_manager_ptr

pimpl<weather_manager> game::weather_manager_ptr
private

Definition at line 958 of file game.h.

◆ zones_manager_open

bool game::zones_manager_open = false
private

Is Zone manager open or not - changes graphics of some zone tiles.

Definition at line 1052 of file game.h.

Referenced by is_zones_manager_open(), and zones_manager().


The documentation for this class was generated from the following files: